# (c) cavaliba.com - tests / app_data.ipam.get_vlan_subnet_hierarchies

from django.test import TestCase

import app_home.cache as cache
from app_data.data import Instance
from app_data.ipam import get_vlan_subnet_hierarchies
from tests import helper


class IpamVlanSubnetHierarchiesTest(TestCase):
    def setUp(self):
        cache.clear()
        # TEST-NET-3 (RFC 5737) - guaranteed not to overlap the builtin
        # 10.0.0.0/8, 192.168.0.0/16, 172.16.0.0/12 seeds (220-ipam.yml)
        helper.add_instance(
            classname="ipam_subnet",
            keyname="203.0.113.0/24",
            fields={"subnet": "203.0.113.0/24", "description": "parent"},
        )
        helper.add_instance(
            classname="ipam_subnet",
            keyname="203.0.113.0/28",
            fields={"subnet": "203.0.113.0/28", "description": "first"},
        )
        helper.add_instance(
            classname="ipam_subnet",
            keyname="203.0.113.16/28",
            fields={"subnet": "203.0.113.16/28", "description": "second"},
        )

    def test_one_hierarchy_per_linked_subnet(self):
        helper.add_instance(
            classname="ipam_vlan",
            keyname="vlan_multi",
            fields={
                "displayname": "Multi VLAN",
                "subnet": ["203.0.113.0/28", "203.0.113.16/28"],
            },
        )
        vlan = Instance.from_keyname(classname="ipam_vlan", keyname="vlan_multi")

        result = get_vlan_subnet_hierarchies(vlan)

        self.assertEqual(len(result), 2)
        keynames = {item["subnet_keyname"] for item in result}
        self.assertEqual(keynames, {"203.0.113.0/28", "203.0.113.16/28"})

    def test_each_hierarchy_starts_at_its_own_subnet(self):
        helper.add_instance(
            classname="ipam_vlan",
            keyname="vlan_single",
            fields={"displayname": "Single VLAN", "subnet": ["203.0.113.0/28"]},
        )
        vlan = Instance.from_keyname(classname="ipam_vlan", keyname="vlan_single")

        result = get_vlan_subnet_hierarchies(vlan)

        self.assertEqual(len(result), 1)
        hierarchy = result[0]["hierarchy"]
        self.assertEqual(
            [h["keyname"] for h in hierarchy],
            ["0.0.0.0/0", "203.0.113.0/24", "203.0.113.0/28"],
        )
        self.assertTrue(hierarchy[-1]["is_containing"])

    def test_no_subnet_field_returns_empty(self):
        helper.add_instance(
            classname="ipam_vlan", keyname="vlan_empty", fields={"displayname": "Empty VLAN"}
        )
        vlan = Instance.from_keyname(classname="ipam_vlan", keyname="vlan_empty")

        self.assertEqual(get_vlan_subnet_hierarchies(vlan), [])

    def test_unknown_subnet_keyname_skipped(self):
        helper.add_instance(
            classname="ipam_vlan",
            keyname="vlan_dangling",
            fields={"displayname": "Dangling VLAN", "subnet": ["203.0.113.0/28"]},
        )
        vlan = Instance.from_keyname(classname="ipam_vlan", keyname="vlan_dangling")

        from app_data.models import DataInstance

        DataInstance.objects.filter(classname="ipam_subnet", keyname="203.0.113.0/28").delete()

        self.assertEqual(get_vlan_subnet_hierarchies(vlan), [])
