def test_use_tag__success(self, mock_is_tag_available): """Test use_tag method to success case.""" mock_is_tag_available.side_effect = [True, True] link = Link(self.iface1, self.iface2) result = link.use_tag(Mock()) self.assertTrue(result)
def test_use_tag__error(self, mock_is_tag_available): """Test use_tag method to error case.""" mock_is_tag_available.side_effect = [True, False] link = Link(self.iface1, self.iface2) result = link.use_tag(Mock()) self.assertFalse(result)
def get_topology_with_metadata(): """Create a topology with metadata.""" switches = {} interfaces = {} links = {} links_to_interfaces, links_to_metadata, switches_to_interface_counts = topology_setting( ) for switch in switches_to_interface_counts: switches[switch] = Switch(switch) for key, value in switches_to_interface_counts.items(): switches[key].interfaces = {} for i in range(1, value + 1): str1 = "{}:{}".format(switches[key].dpid, i) interface = Interface(str1, i, switches[key]) switches[key].update_interface(interface) interfaces[interface.id] = interface i = 0 for interfaces_str in links_to_interfaces: interface_a = interfaces[interfaces_str[0]] interface_b = interfaces[interfaces_str[1]] links[str(i)] = Link(interface_a, interface_b) links[str(i)].metadata = links_to_metadata[i] i += 1 topology = MagicMock() topology.links = links topology.switches = switches return topology
def test_get_next_available_tag(self): """Test get next available tags returns different tags""" link = Link(self.iface1, self.iface2) tag = link.get_next_available_tag() next_tag = link.get_next_available_tag() self.assertNotEqual(tag, next_tag)
def test_init_with_null_endpoints(self): """Test initialization with None as endpoints.""" with self.assertRaises(KytosLinkCreationError): Link(self.iface1, None) with self.assertRaises(KytosLinkCreationError): Link(None, self.iface2)
def test_make_tag_available__error(self, *args): """Test make_tag_available method to error case.""" mock_is_tag_available, _ = args mock_is_tag_available.side_effect = [True, True] link = Link(self.iface1, self.iface2) result = link.make_tag_available(Mock()) self.assertFalse(result)
def test_get_tag_multiple_calls(self): """Test get next available tags returns different tags""" link = Link(self.iface1, self.iface2) tag = link.get_next_available_tag() self.assertEqual(tag.value, 1) next_tag = link.get_next_available_tag() self.assertEqual(next_tag.value, 2)
def test_get_available_vlans(self): """Test _get_available_vlans method.""" link = Link(self.iface1, self.iface2) tag_1 = Mock(tag_type=TAGType.VLAN) tag_2 = Mock(tag_type=TAGType.VLAN_QINQ) tag_3 = Mock(tag_type=TAGType.MPLS) link.endpoint_a.available_tags = [tag_1, tag_2, tag_3] vlans = link._get_available_vlans(link.endpoint_a) self.assertEqual(vlans, [tag_1])
def link_from_dict(self, link_dict): """Return a Link object from python dict.""" id_a = link_dict.get('endpoint_a') id_b = link_dict.get('endpoint_b') endpoint_a = self.controller.get_interface_by_id(id_b) endpoint_b = self.controller.get_interface_by_id(id_a) link = Link(endpoint_a, endpoint_b) link.extend_metadata(link_dict.get('metadata')) return link
def test_concurrent_get_next_tag(self): """Test get next available tags in concurrent execution""" # pylint: disable=import-outside-toplevel from tests.helper import test_concurrently _link = Link(self.iface1, self.iface2) _i = [] _initial_size = len(_link.endpoint_a.available_tags) @test_concurrently(20) def test_get_next_available_tag(): """Assert that get_next_available_tag() returns different tags.""" _i.append(1) _i_len = len(_i) tag = _link.get_next_available_tag() time.sleep(0.0001) _link.use_tag(tag) next_tag = _link.get_next_available_tag() _link.use_tag(next_tag) self.assertNotEqual(tag, next_tag) test_get_next_available_tag() # sleep not needed because test_concurrently waits for all threads # to finish before returning. # time.sleep(0.1) # Check if after the 20th iteration we have 40 tags # It happens because we get 2 tags for every iteration self.assertEqual(_initial_size, len(_link.endpoint_a.available_tags) + 40)
def test_concurrent_get_next_tag(self): """Test get next available tags in concurrent execution""" from tests.helper import test_concurrently _link = Link(self.iface1, self.iface2) _i = [] @test_concurrently(20) def test_get_next_available_tag(): """Test get next availabe tags returns different tags""" _i.append(1) _i_len = len(_i) tag = _link.get_next_available_tag() time.sleep(0.0001) _link.use_tag(tag) next_tag = _link.get_next_available_tag() _link.use_tag(next_tag) self.assertNotEqual(tag, next_tag) # Check if in the 20 iteration the tag value is 40 # It happens because we get 2 tags for every iteration if _i_len == 20: self.assertEqual(next_tag.value, 40) test_get_next_available_tag()
def _get_link_or_create(self, endpoint_a, endpoint_b): new_link = Link(endpoint_a, endpoint_b) for link in self.links.values(): if new_link == link: return link self.links[new_link.id] = new_link return new_link
def test_available_tags(self): """Test available_tags property.""" link = Link(self.iface1, self.iface2) tag_1 = Mock(tag_type=TAGType.VLAN) tag_2 = Mock(tag_type=TAGType.VLAN) tag_3 = Mock(tag_type=TAGType.VLAN_QINQ) tag_4 = Mock(tag_type=TAGType.MPLS) link.endpoint_a.available_tags = [tag_1, tag_2, tag_3, tag_4] link.endpoint_b.available_tags = [tag_2, tag_3, tag_4] self.assertEqual(link.available_tags, [tag_2, tag_3, tag_4])
def test_next_tag_with_use_tags(self): """Test get next availabe tags returns different tags""" link = Link(self.iface1, self.iface2) tag = link.get_next_available_tag() is_available = link.is_tag_available(tag) self.assertFalse(is_available) link.use_tag(tag)
def test_tag_life_cicle(self): """Test get next available tags returns different tags""" link = Link(self.iface1, self.iface2) tag = link.get_next_available_tag() is_available = link.is_tag_available(tag) self.assertFalse(is_available) link.make_tag_available(tag) is_available = link.is_tag_available(tag) self.assertTrue(is_available)
def generate_topology(): """Generates a predetermined topology""" switches = {} interfaces = {} links = {} TestResults.create_switch("S1", switches) TestResults.add_interfaces(2, switches["S1"], interfaces) TestResults.create_switch("S2", switches) TestResults.add_interfaces(3, switches["S2"], interfaces) TestResults.create_switch("S3", switches) TestResults.add_interfaces(2, switches["S3"], interfaces) TestResults.create_switch("S4", switches) TestResults.add_interfaces(2, switches["S4"], interfaces) TestResults.create_switch("S5", switches) links["S1:1<->S2:1"] = Link(interfaces["S1:1"], interfaces["S2:1"]) links["S1:1<->S2:1"].extend_metadata({ "bandwidth": 50, "ownership": "red" }) links["S3:1<->S2:2"] = Link(interfaces["S3:1"], interfaces["S2:2"]) links["S3:1<->S2:2"].extend_metadata({ "bandwidth": 51, "ownership": "blue" }) links["S1:2<->S3:2"] = Link(interfaces["S1:2"], interfaces["S3:2"]) links["S1:2<->S3:2"].extend_metadata({ "bandwidth": 49, "ownership": "blue" }) return switches, links
def create_path(cls, path): """Return the path containing only the interfaces.""" new_path = Path() clean_path = cls._clear_path(path) if len(clean_path) % 2: return None for link in zip(clean_path[1:-1:2], clean_path[2::2]): interface_a = cls.controller.get_interface_by_id(link[0]) interface_b = cls.controller.get_interface_by_id(link[1]) if interface_a is None or interface_b is None: return None new_path.append(Link(interface_a, interface_b)) return new_path
def link_from_dict(link_dict, controller): """Create a link instance from a dictionary.""" endpoint_a = controller.get_interface_by_id( link_dict['endpoint_a']['id']) endpoint_b = controller.get_interface_by_id( link_dict['endpoint_b']['id']) link = Link(endpoint_a, endpoint_b) if 'metadata' in link_dict: link.extend_metadata(link_dict['metadata']) s_vlan = link.get_metadata('s_vlan') if s_vlan: tag = TAG.from_dict(s_vlan) link.update_metadata('s_vlan', tag) return link
def test_id(self): """Test id property.""" link = Link(self.iface1, self.iface2) ids = [] for value in [('A', 1, 'B', 2), ('B', 2, 'A', 1), ('A', 1, 'A', 2), ('A', 2, 'A', 1)]: link.endpoint_a.switch.dpid = value[0] link.endpoint_a.port_number = value[1] link.endpoint_b.switch.dpid = value[2] link.endpoint_b.port_number = value[3] ids.append(link.id) self.assertEqual(ids[0], ids[1]) self.assertEqual(ids[2], ids[3]) self.assertNotEqual(ids[0], ids[2])
def test__eq__(self): """Test __eq__ method.""" link_1 = Link(self.iface1, self.iface2) link_2 = Link(self.iface2, self.iface1) iface1, iface2 = self._get_v0x04_ifaces() iface1.port_number = 1 iface2.port_number = 2 link_3 = Link(iface1, iface2) self.assertTrue(link_1.__eq__(link_2)) self.assertFalse(link_1.__eq__(link_3))
def _link_from_dict(self, link_dict): """Return a Link object from python dict.""" id_a = link_dict.get("endpoint_a").get("id") id_b = link_dict.get("endpoint_b").get("id") endpoint_a = self.controller.get_interface_by_id(id_a) endpoint_b = self.controller.get_interface_by_id(id_b) link = Link(endpoint_a, endpoint_b) if "metadata" in link_dict: link.extend_metadata(link_dict.get("metadata")) s_vlan = link.get_metadata("s_vlan") if s_vlan: tag = TAG.from_dict(s_vlan) if tag is False: error_msg = f"Could not instantiate tag from dict {s_vlan}" raise ValueError(error_msg) link.update_metadata("s_vlan", tag) return link
def _link_from_dict(self, link_dict): """Return a Link object from python dict.""" id_a = link_dict.get('endpoint_a').get('id') id_b = link_dict.get('endpoint_b').get('id') endpoint_a = self.controller.get_interface_by_id(id_a) endpoint_b = self.controller.get_interface_by_id(id_b) link = Link(endpoint_a, endpoint_b) if 'metadata' in link_dict: link.extend_metadata(link_dict.get('metadata')) s_vlan = link.get_metadata('s_vlan') if s_vlan: tag = TAG.from_dict(s_vlan) if tag is False: error_msg = f'Could not instantiate tag from dict {s_vlan}' raise ValueError(error_msg) link.update_metadata('s_vlan', tag) return link
def create_link(interface_a, interface_b, interfaces, links): """Add a new link between two interfaces into the list of links""" compounded = "{}|{}".format(interface_a, interface_b) final_name = compounded links[final_name] = Link( interfaces[interface_a], interfaces[interface_b])
def _fill_links(links, interfaces): links["S1:1<->S2:1"] = Link(interfaces["S1:1"], interfaces["S2:1"]) links["S1:2<->User1:1"] = Link(interfaces["S1:2"], interfaces["User1:1"]) links["S2:2<->User4:1"] = Link(interfaces["S2:2"], interfaces["User4:1"]) links["S3:1<->S5:1"] = Link(interfaces["S3:1"], interfaces["S5:1"]) links["S3:2<->S7:1"] = Link(interfaces["S3:2"], interfaces["S7:1"]) links["S3:3<->S8:1"] = Link(interfaces["S3:3"], interfaces["S8:1"]) links["S3:4<->S11:1"] = Link(interfaces["S3:4"], interfaces["S11:1"]) links["S3:5<->User3:1"] = Link(interfaces["S3:5"], interfaces["User3:1"]) links["S3:6<->User4:2"] = Link(interfaces["S3:6"], interfaces["User4:2"]) links["S4:1<->S5:2"] = Link(interfaces["S4:1"], interfaces["S5:2"]) links["S4:2<->User1:2"] = Link(interfaces["S4:2"], interfaces["User1:2"]) links["S5:3<->S6:1"] = Link(interfaces["S5:3"], interfaces["S6:1"]) links["S5:4<->S6:2"] = Link(interfaces["S5:4"], interfaces["S6:2"]) links["S5:5<->S8:2"] = Link(interfaces["S5:5"], interfaces["S8:2"]) links["S5:6<->User1:3"] = Link(interfaces["S5:6"], interfaces["User1:3"]) links["S6:3<->S9:1"] = Link(interfaces["S6:3"], interfaces["S9:1"]) links["S6:4<->S9:2"] = Link(interfaces["S6:4"], interfaces["S9:2"]) links["S6:5<->S10:1"] = Link(interfaces["S6:5"], interfaces["S10:1"]) links["S7:2<->S8:3"] = Link(interfaces["S7:2"], interfaces["S8:3"]) links["S8:4<->S9:3"] = Link(interfaces["S8:4"], interfaces["S9:3"]) links["S8:5<->S9:4"] = Link(interfaces["S8:5"], interfaces["S9:4"]) links["S8:6<->S10:2"] = Link(interfaces["S8:6"], interfaces["S10:2"]) links["S8:7<->S11:2"] = Link(interfaces["S8:7"], interfaces["S11:2"]) links["S8:8<->User3:2"] = Link(interfaces["S8:8"], interfaces["User3:2"]) links["S10:3<->User2:1"] = Link(interfaces["S10:3"], interfaces["User2:1"]) links["S11:3<->User2:2"] = Link(interfaces["S11:3"], interfaces["User2:2"]) links["User1:4<->User4:3"] = Link(interfaces["User1:4"], interfaces["User4:3"])
def test_init(self): """Test normal Link initialization.""" link = Link(self.iface1, self.iface2) self.assertIsInstance(link, Link) self.assertIs(link.is_active(), True) self.assertIs(link.is_enabled(), False)
def test_link_id(self): """Test equality of links with the same values in different order.""" link1 = Link(self.iface1, self.iface2) link2 = Link(self.iface2, self.iface1) self.assertEqual(link1.id, link2.id)
def test_init_with_null_endpoints(self): """Test initialization with None as endpoints.""" with self.assertRaises(ValueError): Link(None, None)
def test__repr__(self): """Test __repr__ method.""" link = Link(self.iface1, self.iface2) expected = ("Link(Interface('interface1', 41, Switch('dpid1')), " "Interface('interface2', 42, Switch('dpid2')))") self.assertEqual(repr(link), expected)
def generateTopology(): """Generates a predetermined topology""" switches = {} interfaces = {} links = {} TestKytosGraph.createSwitch("S1", switches) TestKytosGraph.addInterfaces(2, switches["S1"], interfaces) TestKytosGraph.createSwitch("S2", switches) TestKytosGraph.addInterfaces(2, switches["S2"], interfaces) TestKytosGraph.createSwitch("S3", switches) TestKytosGraph.addInterfaces(6, switches["S3"], interfaces) TestKytosGraph.createSwitch("S4", switches) TestKytosGraph.addInterfaces(2, switches["S4"], interfaces) TestKytosGraph.createSwitch("S5", switches) TestKytosGraph.addInterfaces(6, switches["S5"], interfaces) TestKytosGraph.createSwitch("S6", switches) TestKytosGraph.addInterfaces(5, switches["S6"], interfaces) TestKytosGraph.createSwitch("S7", switches) TestKytosGraph.addInterfaces(2, switches["S7"], interfaces) TestKytosGraph.createSwitch("S8", switches) TestKytosGraph.addInterfaces(8, switches["S8"], interfaces) TestKytosGraph.createSwitch("S9", switches) TestKytosGraph.addInterfaces(4, switches["S9"], interfaces) TestKytosGraph.createSwitch("S10", switches) TestKytosGraph.addInterfaces(3, switches["S10"], interfaces) TestKytosGraph.createSwitch("S11", switches) TestKytosGraph.addInterfaces(3, switches["S11"], interfaces) TestKytosGraph.createSwitch("User1", switches) TestKytosGraph.addInterfaces(4, switches["User1"], interfaces) TestKytosGraph.createSwitch("User2", switches) TestKytosGraph.addInterfaces(2, switches["User2"], interfaces) TestKytosGraph.createSwitch("User3", switches) TestKytosGraph.addInterfaces(2, switches["User3"], interfaces) TestKytosGraph.createSwitch("User4", switches) TestKytosGraph.addInterfaces(3, switches["User4"], interfaces) links["S1:1<->S2:1"] = Link(interfaces["S1:1"], interfaces["S2:1"]) links["S1:1<->S2:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 105 }) links["S1:2<->User1:1"] = Link(interfaces["S1:2"], interfaces["User1:1"]) links["S1:2<->User1:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S2:2<->User4:1"] = Link(interfaces["S2:2"], interfaces["User4:1"]) links["S2:2<->User4:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 10 }) links["S3:1<->S5:1"] = Link(interfaces["S3:1"], interfaces["S5:1"]) links["S3:1<->S5:1"].extend_metadata({ "reliability": 5, "bandwidth": 10, "delay": 112 }) links["S3:2<->S7:1"] = Link(interfaces["S3:2"], interfaces["S7:1"]) links["S3:2<->S7:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S3:3<->S8:1"] = Link(interfaces["S3:3"], interfaces["S8:1"]) links["S3:3<->S8:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S3:4<->S11:1"] = Link(interfaces["S3:4"], interfaces["S11:1"]) links["S3:4<->S11:1"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 6 }) links["S3:5<->User3:1"] = Link(interfaces["S3:5"], interfaces["User3:1"]) links["S3:5<->User3:1"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S3:6<->User4:2"] = Link(interfaces["S3:6"], interfaces["User4:2"]) links["S3:6<->User4:2"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 10 }) links["S4:1<->S5:2"] = Link(interfaces["S4:1"], interfaces["S5:2"]) links["S4:1<->S5:2"].extend_metadata({ "reliability": 1, "bandwidth": 100, "delay": 30, "ownership": "A" }) links["S4:2<->User1:2"] = Link(interfaces["S4:2"], interfaces["User1:2"]) links["S4:2<->User1:2"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 110, "ownership": "A" }) links["S5:3<->S6:1"] = Link(interfaces["S5:3"], interfaces["S6:1"]) links["S5:3<->S6:1"].extend_metadata({ "reliability": 1, "bandwidth": 100, "delay": 40 }) links["S5:4<->S6:2"] = Link(interfaces["S5:4"], interfaces["S6:2"]) links["S5:4<->S6:2"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 40, "ownership": "A" }) links["S5:5<->S8:2"] = Link(interfaces["S5:5"], interfaces["S8:2"]) links["S5:5<->S8:2"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 112 }) links["S5:6<->User1:3"] = Link(interfaces["S5:6"], interfaces["User1:3"]) links["S5:6<->User1:3"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 60 }) links["S6:3<->S9:1"] = Link(interfaces["S6:3"], interfaces["S9:1"]) links["S6:3<->S9:1"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 60 }) links["S6:4<->S9:2"] = Link(interfaces["S6:4"], interfaces["S9:2"]) links["S6:4<->S9:2"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 62 }) links["S6:5<->S10:1"] = Link(interfaces["S6:5"], interfaces["S10:1"]) links["S6:5<->S10:1"].extend_metadata({ "bandwidth": 100, "delay": 108, "ownership": "A" }) links["S7:2<->S8:3"] = Link(interfaces["S7:2"], interfaces["S8:3"]) links["S7:2<->S8:3"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S8:4<->S9:3"] = Link(interfaces["S8:4"], interfaces["S9:3"]) links["S8:4<->S9:3"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 32 }) links["S8:5<->S9:4"] = Link(interfaces["S8:5"], interfaces["S9:4"]) links["S8:5<->S9:4"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 110 }) links["S8:6<->S10:2"] = Link(interfaces["S8:6"], interfaces["S10:2"]) links["S8:6<->S10:2"].extend_metadata({ "reliability": 5, "bandwidth": 100, "ownership": "A" }) links["S8:7<->S11:2"] = Link(interfaces["S8:7"], interfaces["S11:2"]) links["S8:7<->S11:2"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 7 }) links["S8:8<->User3:2"] = Link(interfaces["S8:8"], interfaces["User3:2"]) links["S8:8<->User3:2"].extend_metadata({ "reliability": 5, "bandwidth": 100, "delay": 1 }) links["S10:3<->User2:1"] = Link(interfaces["S10:3"], interfaces["User2:1"]) links["S10:3<->User2:1"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 10, "ownership": "A" }) links["S11:3<->User2:2"] = Link(interfaces["S11:3"], interfaces["User2:2"]) links["S11:3<->User2:2"].extend_metadata({ "reliability": 3, "bandwidth": 100, "delay": 6 }) links["User1:4<->User4:3"] = Link(interfaces["User1:4"], interfaces["User4:3"]) links["User1:4<->User4:3"].extend_metadata({ "reliability": 5, "bandwidth": 10, "delay": 105 }) return (switches, links)
def createLink(interface_a, interface_b, interfaces, links): compounded = "{}|{}".format(interface_a, interface_b) final_name = compounded links[final_name] = Link(interfaces[interface_a], interfaces[interface_b]) print("Creating Link: ", final_name)