def test_description_absent(self):
     """
     Configure any interface to have no description.
     
     Attempt the task exactly once.
     Restore the original description to the interface.
     """
     for device_name in inventory_connected():
         for interface_name in interface_names(device_name):
             original_info = interface_configuration_tuple(
                 device_name, interface_name)
             interface_configuration_update(device_name, interface_name,
                                            None, original_info.address,
                                            original_info.netmask,
                                            original_info.active,
                                            original_info.shutdown)
             modified_info = interface_configuration_tuple(
                 device_name, interface_name)
             self.assertIsNone(modified_info.description)
             interface_configuration_update(device_name, interface_name,
                                            original_info.description,
                                            original_info.address,
                                            original_info.netmask,
                                            original_info.active,
                                            original_info.shutdown)
             return
     self.fail(
         "Expected (at least) one connected device with (at least) one interface."
     )
 def test_description_absent(self):
     """
     Configure any interface to have no description.
     
     Attempt the task exactly once.
     Restore the original description to the interface.
     """
     for device_name in inventory_connected():
         for interface_name in interface_names(device_name):
             original_info = interface_configuration_tuple(device_name, interface_name)
             interface_configuration_update(device_name, interface_name, None, original_info.address, original_info.netmask, original_info.active, original_info.shutdown)
             modified_info = interface_configuration_tuple(device_name, interface_name)
             self.assertIsNone(modified_info.description)
             interface_configuration_update(device_name, interface_name, original_info.description, original_info.address, original_info.netmask, original_info.active, original_info.shutdown)
             return
     self.fail("Expected (at least) one connected device with (at least) one interface.")
def main():
    ''' Select a device and demonstrate.'''
    print(plain(doc(acl_apply_packet_filter)))
    inventory = inventory_acl()
    if not inventory:
        print(
            'There are no ACL capable devices to examine. Demonstration cancelled.'
        )
    else:
        for device_name in inventory:
            mgmt_name = management_interface(device_name)
            acl_names = acl_list(device_name)
            if not acl_names:
                print('Skip device with no ACLs: ', device_name)
                continue
            else:
                random.shuffle(acl_names)
                acl_name = acl_names[0]
            for ic in interface_configuration_tuple(device_name):
                if ic.name == mgmt_name:
                    continue
                print('Consider %s %s in=%s, out=%s' %
                      (device_name, ic.name, ic.packet_filter_inbound,
                       ic.packet_filter_outbound))
                if not ic.packet_filter_outbound:
                    demonstrate(device_name, ic.name, 'outbound', acl_name)
                    return os.EX_OK
                if not ic.packet_filter_inbound:
                    demonstrate(device_name, ic.name, 'inbound', acl_name)
                    return os.EX_OK
        print(
            'There are no network interfaces available to apply an ACL. Demonstration cancelled.'
        )
    return os.EX_TEMPFAIL
def demonstrate(device_name, interface_name):
    ''' Apply function 'interface_configuration_tuple' to the specified device/interface.'''
    print('interface_configuration(' + device_name,
          interface_name,
          sep=', ',
          end=')\n')
    print_table(interface_configuration_tuple(device_name, interface_name))
def main():
    ''' Select a device and demonstrate.'''
    print(plain(doc(acl_apply_packet_filter)))
    inventory = inventory_acl()
    if not inventory:
        print('There are no ACL capable devices to examine. Demonstration cancelled.')
    else:
        for device_name in inventory:
            mgmt_name = management_interface(device_name)
            acl_names = acl_list(device_name)
            if not acl_names:
                print('Skip device with no ACLs: ', device_name)
                continue
            else:
                random.shuffle(acl_names)
                acl_name = acl_names[0]
            for ic in interface_configuration_tuple(device_name):
                if ic.name == mgmt_name:
                    continue
                print('Consider %s %s in=%s, out=%s' % (device_name, ic.name, ic.packet_filter_inbound, ic.packet_filter_outbound))
                if not ic.packet_filter_outbound:
                    demonstrate(device_name, ic.name, 'outbound', acl_name)
                    return EX_OK
                if not ic.packet_filter_inbound:
                    demonstrate(device_name, ic.name, 'inbound', acl_name)
                    return EX_OK
        print('There are no network interfaces available to apply an ACL. Demonstration cancelled.')
    return EX_TEMPFAIL
def demonstrate(device_name):
    """
    Apply function 'static_route_create' to the specified device.
    
    Choose a destination that does not already exist. 
    Choose a next-hop on the same sub-network as an existing interface.
    If the next-hop is unknown then use any valid ip-address.
    """
    
    print('Select a destination network for which a static route does not exist.')
    destination_network_iterator = destination_network_generator()
    while True: 
        destination_network = next(destination_network_iterator)
        print('static_route_exists(%s, %s)' % (device_name, destination_network))
        exists = static_route_exists(device_name, destination_network)
        print(exists)
        print()
        if not exists:
            break
    
    print('Determine which interface is on the management plane (to avoid it).')     
    print('device_control(%s)' % device_name)
    device_mgmt = device_control(device_name)
    print_table(device_mgmt)
    print()

    print('Determine ip-address and network-mask of every interface.')     
    print('interface_configuration_tuple(%s)' % device_name)
    interface_config_list = interface_configuration_tuple(device_name)
    print_table(interface_config_list)
    print()
    
    for interface_config in interface_config_list:
        if interface_config.address is None:
            # Skip network interface with unassigned IP address.             
            continue
        if interface_config.address == device_mgmt.address:
            # Do not configure static routes on the 'management plane'.             
            continue
        if 'Loopback' in interface_config.name:
            # Do not configure static routes on the 'control plane'.             
            continue
        
        print('Determine next-hop for a network interface.')
        interface_network = interface_config.ip_network
        next_hop_address = match(device_name, interface_network)
        if next_hop_address is None:
            print('Next-hop for %s/%s %s/%s is outside the known topology.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask))
            next_hop_address = interface_network.network_address
            if next_hop_address == interface_config.ip_interface:
                next_hop_address += 1
            print('Assume that next-hop for %s/%s %s/%s is %s.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask, next_hop_address))
        else:
            print('Next-hop for %s/%s %s/%s is %s.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask, next_hop_address))
        print()

        print('static_route_create(%s, %s, %s)' % (device_name, destination_network, next_hop_address))
        static_route_create(device_name, destination_network, next_hop_address)
        return True
    return False
예제 #7
0
def demonstrate(device_name, interface_config):
    print("Initial configuration:")
    initial = interface_config
    print(initial)
    assert not initial.shutdown

    print()
    print("Shutdown interface %s on %s:" % (initial.name, device_name))
    print('interface_configuration_update(' + device_name,
          initial.name,
          initial.description,
          initial.address,
          initial.netmask,
          shutdown,
          sep=', ',
          end=')\n')
    interface_configuration_update(device_name,
                                   initial.name,
                                   description=initial.description,
                                   address=initial.address,
                                   netmask=initial.netmask,
                                   shutdown=shutdown)
    print()
    print("Modified configuration:")
    modified = interface_configuration_tuple(device_name, initial.name)
    print(modified)
    assert modified.shutdown
def demonstrate(device_name):
    """
    Apply function 'static_route_create' to the specified device.
    
    Choose a destination that does not already exist. 
    Choose a next-hop on the same sub-network as an existing interface.
    If the next-hop is unknown then use any valid ip-address.
    """
    
    print('Select a destination network for which a static route does not exist.')
    destination_network_iterator = destination_network_generator()
    while True: 
        destination_network = next(destination_network_iterator)
        print('static_route_exists(%s, %s)' % (device_name, destination_network))
        exists = static_route_exists(device_name, destination_network)
        print(exists)
        print()
        if not exists:
            break
    
    print('Determine which interface is on the management plane (to avoid it).')     
    print('device_control(%s)' % device_name)
    device_mgmt = device_control(device_name)
    print_table(device_mgmt)
    print()

    print('Determine ip-address and network-mask of every interface.')     
    print('interface_configuration_tuple(%s)' % device_name)
    interface_config_list = interface_configuration_tuple(device_name)
    print_table(interface_config_list)
    print()
    
    for interface_config in interface_config_list:
        if interface_config.address is None:
            # Skip network interface with unassigned IP address.             
            continue
        if interface_config.address == device_mgmt.address:
            # Do not configure static routes on the 'management plane'.             
            continue
        if 'Loopback' in interface_config.name:
            # Do not configure static routes on the 'control plane'.             
            continue
        
        print('Determine next-hop for a network interface.')
        interface_network = interface_config.ip_network
        next_hop_address = match(device_name, interface_network)
        if next_hop_address is None:
            print('Next-hop for %s/%s %s/%s is outside the known topology.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask))
            next_hop_address = interface_network.network_address
            if next_hop_address == interface_config.ip_interface:
                next_hop_address += 1
            print('Assume that next-hop for %s/%s %s/%s is %s.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask, next_hop_address))
        else:
            print('Next-hop for %s/%s %s/%s is %s.' % (device_name, interface_config.name, interface_config.address, interface_config.netmask, next_hop_address))
        print()

        print('static_route_create(%s, %s, %s)' % (device_name, destination_network, next_hop_address))
        static_route_create(device_name, destination_network, next_hop_address)
        return True
    return False
예제 #9
0
def demonstrate(device_name, interface_name):
    print("Initial configuration:")
    print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
    initial = interface_configuration_tuple(device_name, interface_name)
    print(initial)
    
    try:
        print()
        print("Modify configuration:")
        print('interface_configuration_update(%s, %s, %s, %s, %s, %s)' % (device_name, interface_name, temp_description, temp_address, temp_netmask, not initial.shutdown))
        interface_configuration_update(device_name, initial.name, description=temp_description,
                               address=temp_address, netmask=temp_netmask, shutdown=not initial.shutdown)
        print()
        print("Modified configuration:")
        print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
        modified = interface_configuration_tuple(device_name, initial.name)
        print(modified)
        assert modified.name == initial.name
        assert modified.description != initial.description
        assert modified.address != initial.address
        assert modified.netmask != initial.netmask
        assert modified.shutdown != initial.shutdown
        
    finally:
        print()
        print("Restore configuration:")
        print('interface_configuration_update(%s, %s, %s, %s, %s, %s)' % (device_name, interface_name, initial.description, initial.address, initial.netmask, initial.shutdown))
        interface_configuration_update(device_name, interface_name, description=initial.description, address=initial.address, netmask=initial.netmask, shutdown=initial.shutdown)
    
        print()
        print("Restored configuration:")
        print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
        restored = interface_configuration_tuple(device_name, interface_name)
        print(restored)
        assert restored.name == initial.name
        assert restored.description == initial.description, "Expected '%s' %s got '%s' %s" % (initial.description, type(initial.description), restored.description, type(restored.description))
        assert restored.address == initial.address
        assert restored.netmask == initial.netmask
        assert restored.shutdown == initial.shutdown
        assert restored.active == initial.active
def demonstrate(device_name, interface_name):
    print("Initial configuration:")
    print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
    initial = interface_configuration_tuple(device_name, interface_name)
    print(initial)
    
    try:
        print()
        print("Modify configuration:")
        print('interface_configuration_update(%s, %s, %s, %s, %s, %s)' % (device_name, interface_name, temp_description, temp_address, temp_netmask, not initial.shutdown))
        interface_configuration_update(device_name, initial.name, description=temp_description,
                               address=temp_address, netmask=temp_netmask, shutdown=not initial.shutdown)
        print()
        print("Modified configuration:")
        print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
        modified = interface_configuration_tuple(device_name, initial.name)
        print(modified)
        assert modified.name == initial.name
        assert modified.description != initial.description
        assert modified.address != initial.address
        assert modified.netmask != initial.netmask
        assert modified.shutdown != initial.shutdown
        
    finally:
        print()
        print("Restore configuration:")
        print('interface_configuration_update(%s, %s, %s, %s, %s, %s)' % (device_name, interface_name, initial.description, initial.address, initial.netmask, initial.shutdown))
        interface_configuration_update(device_name, interface_name, description=initial.description, address=initial.address, netmask=initial.netmask, shutdown=initial.shutdown)
    
        print()
        print("Restored configuration:")
        print('interface_configuration_tuple(%s, %s):' % (device_name, interface_name))
        restored = interface_configuration_tuple(device_name, interface_name)
        print(restored)
        assert restored.name == initial.name
        assert restored.description == initial.description, "Expected '%s' %s got '%s' %s" % (initial.description, type(initial.description), restored.description, type(restored.description))
        assert restored.address == initial.address
        assert restored.netmask == initial.netmask
        assert restored.shutdown == initial.shutdown
        assert restored.active == initial.active
 def test_interface_configuration_tuple(self):
     device_names = inventory_connected()
     self.assertTrue(device_names, "Expected one or more connected devices.")
     interface_count = 0
     for device_name in device_names:
         for interface_name in interface_names(device_name):
             info = interface_configuration_tuple(device_name, interface_name)
             self.assertEqual(info.name, interface_name)
             self.assertTrue(info.description is None or isinstance(info.description, str))
             self.assertTrue(info.address is None or isinstance(info.address, str))
             self.assertTrue(info.netmask is None or isinstance(info.netmask, str))
             interface_count+=1
     self.assertNotEqual(0, interface_count, 'Expected one or more interfaces.')
def match(device_name, interface_network):
    """ Discover matching interface on a different device."""
    for other_device in inventory_mounted():
        if other_device == device_name:
            continue
        for interface_name in interface_names(other_device):
            interface_config = interface_configuration_tuple(other_device, interface_name)
            if interface_config.address is None:
                # Skip network interface with unassigned IP address.             
                continue
            other_network = to_ip_network(interface_config.address, interface_config.netmask)
            if other_network == interface_network:
                print('Match %s/%s/%s to %s/%s' % (device_name, interface_config.address, interface_config.netmask, \
                                                   other_device, interface_network))
                return interface_config.address
    return None
def demonstrate(device_name, interface_config):
    print("Initial configuration:")
    initial = interface_config
    print(initial)
    assert not initial.shutdown

    print()
    print("Shutdown interface %s on %s:" % (initial.name, device_name))
    print('interface_configuration_update(' + device_name, initial.name, initial.description, initial.address, initial.netmask, shutdown, sep=', ', end=')\n')
    interface_configuration_update(device_name, initial.name, description=initial.description,
                           address=initial.address, netmask=initial.netmask, shutdown=shutdown)
    print()
    print("Modified configuration:")
    modified = interface_configuration_tuple(device_name, initial.name)
    print(modified)
    assert modified.shutdown
def match(device_name, interface_network):
    """ Discover matching interface on a different device."""
    for other_device in inventory_mounted():
        if other_device == device_name:
            continue
        for interface_name in interface_names(other_device):
            interface_config = interface_configuration_tuple(other_device, interface_name)
            if interface_config.address is None:
                # Skip network interface with unassigned IP address.             
                continue
            other_network = to_ip_network(interface_config.address, interface_config.netmask)
            if other_network == interface_network:
                print('Match %s/%s/%s to %s/%s' % (device_name, interface_config.address, interface_config.netmask, \
                                                   other_device, interface_network))
                return interface_config.address
    return None
def sample_destination(device_name):
    """ Determine a suitable destination for a static route from the specified network device. """
    # Implementation: use 'next subnet' of any data interface on the specified device.
    mgmt_name = management_interface(device_name)
    interface_list = interface_names(device_name)
    for interface_name in interface_list:
        if interface_name == mgmt_name:
            # Do not configure static routes on the control plane.
            continue
        config = interface_configuration_tuple(device_name, interface_name)
        if config.address is None:
            # Skip network interface with unassigned IP address.
            continue
        interface_network = to_ip_network(config.address, config.netmask)
        destination_network = next_subnet(interface_network)
        return destination_network
    return None
def sample_destination(device_name):
    """ Determine a suitable destination for a static route from the specified network device. """
    # Implementation: use 'next subnet' of any data interface on the specified device.
    mgmt_name = management_interface(device_name)
    interface_list = interface_names(device_name)
    for interface_name in interface_list:
        if interface_name == mgmt_name:
            # Do not configure static routes on the control plane.             
            continue
        config = interface_configuration_tuple(device_name, interface_name)
        if config.address is None:
            # Skip network interface with unassigned IP address.             
            continue
        interface_network = to_ip_network(config.address, config.netmask)
        destination_network = next_subnet(interface_network)
        return destination_network
    return None
def main():
    print(plain(doc(interface_configuration_update)))
    for device_name in inventory_connected():
        mgmt_name = management_interface(device_name)
        for interface_name in interface_names(device_name):
            # Choose interface on 'data plane' not 'control plane'.
            if interface_name == mgmt_name:
                continue
            interface_config = interface_configuration_tuple(device_name, interface_name)
            if not interface_config.address:
                continue
            if not interface_config.shutdown:
                continue
            demonstrate(device_name, interface_config)
            return EX_OK
    print("There are no suitable network devices/interfaces. Demonstration cancelled.")
    return EX_TEMPFAIL
def main():
    print(plain(doc(interface_configuration_update)))
    for device_name in inventory_connected():
        mgmt_name = management_interface(device_name)
        for interface_name in interface_names(device_name):
            # Choose interface on 'data plane' not 'control plane'.
            if interface_name == mgmt_name:
                continue
            interface_config = interface_configuration_tuple(device_name, interface_name)
            if not interface_config.address:
                continue
            if interface_config.shutdown:
                continue
            demonstrate(device_name, interface_config)
            return os.EX_OK
    print("There are no suitable network devices/interfaces. Demonstration cancelled.")
    return os.EX_TEMPFAIL
def main():
    ''' Select a device and demonstrate.'''
    print(plain(doc(acl_unapply_packet_filter)))
    inventory = inventory_acl()
    if not inventory:
        print('There are no ACL capable devices to examine. Demonstration cancelled.')
    else:
        for device_name in inventory:
            for ic in interface_configuration_tuple(device_name):
                print('Consider %s %s in=%s, out=%s' % (device_name, ic.name, ic.packet_filter_inbound, ic.packet_filter_outbound))
                if ic.packet_filter_outbound:
                    demonstrate(device_name, ic.name, 'outbound', ic.packet_filter_outbound)
                    return os.EX_OK
                if ic.packet_filter_inbound:
                    demonstrate(device_name, ic.name, 'inbound', ic.packet_filter_inbound)
                    return os.EX_OK
        print('There are no ACLs to unapply. Demonstration cancelled.')
    return os.EX_TEMPFAIL
 def test_interface_configuration_tuple(self):
     device_names = inventory_connected()
     self.assertTrue(device_names,
                     "Expected one or more connected devices.")
     interface_count = 0
     for device_name in device_names:
         for interface_name in interface_names(device_name):
             info = interface_configuration_tuple(device_name,
                                                  interface_name)
             self.assertEqual(info.name, interface_name)
             self.assertTrue(info.description is None
                             or isinstance(info.description, str))
             self.assertTrue(info.address is None
                             or isinstance(info.address, str))
             self.assertTrue(info.netmask is None
                             or isinstance(info.netmask, str))
             interface_count += 1
     self.assertNotEqual(0, interface_count,
                         'Expected one or more interfaces.')
예제 #21
0
def demonstrate(device_name):
    ''' Apply function 'static_route_create' to the specified device for a new destination.'''
    mgmt_name = management_interface(device_name)
    interface_list = interface_names(device_name)
    for interface_name in interface_list:
        if interface_name == mgmt_name:
            # Do not configure static routes on the control plane.             
            continue
        config = interface_configuration_tuple(device_name, interface_name)
        if config.address is None:
            # Skip network interface with unassigned IP address.             
            continue
        print()
        interface_network = to_ip_network(config.address, config.netmask)
        next_hop_address = match(device_name, interface_network)
        if next_hop_address is None:
            print('No end-point for %s/%s/%s/%s' % (device_name, interface_name, config.address, config.netmask))
            continue
        destination_network = static_route_fixture.new_destination(device_name, interface_network)
        print('static_route_create(%s, %s, %s)' % (device_name, destination_network, next_hop_address))
        static_route_create(device_name, destination_network, next_hop_address)
        return True
    return False
예제 #22
0
def main():
    ''' Select a device and demonstrate.'''
    print(plain(doc(acl_unapply_packet_filter)))
    inventory = inventory_acl()
    if not inventory:
        print(
            'There are no ACL capable devices to examine. Demonstration cancelled.'
        )
    else:
        for device_name in inventory:
            for ic in interface_configuration_tuple(device_name):
                print('Consider %s %s in=%s, out=%s' %
                      (device_name, ic.name, ic.packet_filter_inbound,
                       ic.packet_filter_outbound))
                if ic.packet_filter_outbound:
                    demonstrate(device_name, ic.name, 'outbound',
                                ic.packet_filter_outbound)
                    return os.EX_OK
                if ic.packet_filter_inbound:
                    demonstrate(device_name, ic.name, 'inbound',
                                ic.packet_filter_inbound)
                    return os.EX_OK
        print('There are no ACLs to unapply. Demonstration cancelled.')
    return os.EX_TEMPFAIL
예제 #23
0
def main():
    #device_list=settings.config['network_device']
    device_list = settings.config['network_device']
    connected_list = topology.connected_nodes()

    if len(connected_list) != len(device_list):
        print('not all devices are connected!')
        return

    device_1 = 'iosxrv-1'
    device_2 = 'iosxrv-2'
    device_3 = 'iosxrv-3'
    device_4 = 'iosxrv-4'
    device_5 = 'iosxrv-5'
    device_6 = 'iosxrv-6'
    device_7 = 'iosxrv-7'
    device_8 = 'iosxrv-8'
    interface_0 = 'GigabitEthernet0/0/0/0'
    interface_1 = 'GigabitEthernet0/0/0/1'
    interface_2 = 'GigabitEthernet0/0/0/2'
    interface_3 = 'GigabitEthernet0/0/0/3'
    interface_4 = 'GigabitEthernet0/0/0/4'
    interface_5 = 'GigabitEthernet0/0/0/5'
    interface_6 = 'GigabitEthernet0/0/0/6'

    #change path for flow 1
    destination_network = to_ip_network('100.0.0.0', '24')
    prior_next_hop = '10.0.28.2'
    second_next_hop = '10.0.18.1'
    if (interface_configuration_tuple(device_2, interface_2).shutdown
            == False) & (interface_configuration_tuple(
                device_8, interface_2).shutdown == False):
        link_status = 'up'
    else:
        link_status = 'down'
    #loop
    #for i in range(100):
    while True:
        #check the link
        if (interface_configuration_tuple(device_2, interface_2).shutdown
                == False) & (interface_configuration_tuple(
                    device_8, interface_2).shutdown == False):
            new_status = 'up'
            #print('link: device_2 <-> device_8 is OK')
        else:
            new_status = 'down'
            #print('link: device_2 <-> device_8 is fail')

        #link status unchange
        if link_status == new_status:
            print('device_2 <-> device_8 link status unchange')
            time.sleep(1)
            continue
        #link status up -> down
        elif (link_status == 'up') & (new_status == 'down'):
            delete_static_route(device_8, destination_network, 1)
            add_static_route(device_8, destination_network, second_next_hop, 1)
            print(
                'device_2 <-> device_8 link status from up to down: delete prior_route, add second_route, at last for 10s'
            )
            link_status = new_status
            time.sleep(10)
        #link status down -> up
        elif (link_status == 'down') & (new_status == 'up'):
            delete_static_route(device_8, destination_network, 1)
            add_static_route(device_8, destination_network, prior_next_hop, 1)
            print(
                'device_2 <-> device_8 link status from down to up: delete second_route, add prior_route'
            )
            link_status = new_status
            time.sleep(3)
def demonstrate(device_name, interface_name):
    ''' Apply function 'interface_configuration_tuple' to the specified device/interface.'''
    print('interface_configuration(' + device_name, interface_name, sep=', ', end=')\n')
    print_table(interface_configuration_tuple(device_name, interface_name))
def main():
    #device_list=settings.config['network_device']
    device_list = settings.config['network_device']
    connected_list = topology.connected_nodes()
    
    if len(connected_list) != len(device_list):
        print('not all devices are connected!')
        return
    
    device_1 = 'iosxrv-1'
    device_2 = 'iosxrv-2'
    device_3 = 'iosxrv-3'
    device_4 = 'iosxrv-4'
    device_5 = 'iosxrv-5'
    device_6 = 'iosxrv-6'
    device_7 = 'iosxrv-7'
    device_8 = 'iosxrv-8'
    interface_0 = 'GigabitEthernet0/0/0/0'
    interface_1 = 'GigabitEthernet0/0/0/1'
    interface_2 = 'GigabitEthernet0/0/0/2'
    interface_3 = 'GigabitEthernet0/0/0/3'
    interface_4 = 'GigabitEthernet0/0/0/4'
    interface_5 = 'GigabitEthernet0/0/0/5'
    interface_6 = 'GigabitEthernet0/0/0/6'
    
    
    #change path for flow 1
    destination_network = to_ip_network('100.0.0.0', '24')
    prior_next_hop = '10.0.28.2'
    second_next_hop = '10.0.18.1'
    if (interface_configuration_tuple(device_2, interface_2).shutdown == False) & (interface_configuration_tuple(device_8, interface_2).shutdown == False):
        link_status = 'up'
    else:
        link_status = 'down'
    #loop
    #for i in range(100):
    while True:
        #check the link
        if (interface_configuration_tuple(device_2, interface_2).shutdown == False) & (interface_configuration_tuple(device_8, interface_2).shutdown == False):
            new_status = 'up'
            #print('link: device_2 <-> device_8 is OK')
        else:
            new_status = 'down'
            #print('link: device_2 <-> device_8 is fail')
            
        #link status unchange
        if link_status == new_status:
            print('device_2 <-> device_8 link status unchange')
            time.sleep(1)
            continue
        #link status up -> down
        elif (link_status == 'up') & (new_status == 'down'): 
            delete_static_route(device_8, destination_network, 1)
            add_static_route(device_8, destination_network, second_next_hop, 1)
            print('device_2 <-> device_8 link status from up to down: delete prior_route, add second_route, at last for 10s')
            link_status = new_status
            time.sleep(10)
        #link status down -> up
        elif (link_status == 'down') & (new_status == 'up'): 
            delete_static_route(device_8, destination_network, 1)
            add_static_route(device_8, destination_network, prior_next_hop, 1)
            print('device_2 <-> device_8 link status from down to up: delete second_route, add prior_route')
            link_status = new_status
            time.sleep(3)
def main():   
    device_list=settings.config['network_device']
    connected_list = topology.connected_nodes()
    
    if len(connected_list) != len(device_list):
        print('not all devices are connected!')
        return
    
    device_1 = 'iosxrv-1'
    device_2 = 'iosxrv-2'
    device_3 = 'iosxrv-3'
    device_4 = 'iosxrv-4'
    device_5 = 'iosxrv-5'
    device_6 = 'iosxrv-6'
    device_7 = 'iosxrv-7'
    device_8 = 'iosxrv-8'
    interface_0 = 'GigabitEthernet0/0/0/0'
    interface_1 = 'GigabitEthernet0/0/0/1'
    interface_2 = 'GigabitEthernet0/0/0/2'
    interface_3 = 'GigabitEthernet0/0/0/3'
    interface_4 = 'GigabitEthernet0/0/0/4'
    interface_5 = 'GigabitEthernet0/0/0/5'
    interface_6 = 'GigabitEthernet0/0/0/6'
    
    #link device_1 to device_2
    initial = interface_configuration_tuple(device_1, interface_0)
    #print_table(initial)
    ip_address = '10.0.12.1'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_2'
    interface_configuration_update(device_1, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_1, interface_0))
    #link device_2 to device_1
    initial = interface_configuration_tuple(device_2, interface_0)
    #print_table(initial)
    ip_address = '10.0.12.2'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_1'
    interface_configuration_update(device_2, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_2, interface_0))
    #display
    print('set link device_1 <-> device_2')
    
    #link device_1 to device_8
    initial = interface_configuration_tuple(device_1, interface_5)
    #print_table(initial)
    ip_address = '10.0.18.1'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_8'
    interface_configuration_update(device_1, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_1, interface_5))
    #link device_8 to device_1
    initial = interface_configuration_tuple(device_8, interface_1)
    #print_table(initial)
    ip_address = '10.0.18.8'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_1'
    interface_configuration_update(device_8, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_8, interface_1))
    #display
    print('set link device_1 <-> device_8')
    
    #link device_2 to device_8
    initial = interface_configuration_tuple(device_2, interface_2)
    #print_table(initial)
    ip_address = '10.0.28.2'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_8'
    interface_configuration_update(device_2, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_2, interface_2))
    #link device_8 to device_2
    initial = interface_configuration_tuple(device_8, interface_2)
    #print_table(initial)
    ip_address = '10.0.28.8'
    ip_netmask = '255.255.255.0'
    description = 'connect to device_2'
    interface_configuration_update(device_8, initial.name, description=description, address=ip_address, netmask=ip_netmask, shutdown=False)
    print_table(interface_configuration_tuple(device_8, interface_2))
    #display
    print('set link device_2 <-> device_8')