Python Forum

Full Version: Loop through values and compare
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Hi everyone

My 2nd inquiry as I try to learn Python and ways to expand my network engineering toolkit.

I found a script on Packetswitch by Suresh Vina where he connects to a router gets its arp table then connects to a switch and grabs its mac table. Then compares the 2 lists and match mac to switch interface. I am trying to work off of that and take a list of known mac addresses in a csv file and compare to the mac table of a switch. I am able to pull the mac addresses from the csv file and also able to connect to the switch and get the mac table. The issue I am running into is the comparing part. The script runs through with no errors but just not giving me the print statements I am looking for at the end. Below is what I have so far. Any suggestions much appriciated!

 File Contents
50:00:00:0E:80:02
50:00:00:0B:00:00
 Script
from napalm import get_network_driver
import getpass
import json
import csv


#User Input
user = input(">> Username: ")
passw = getpass.getpass(">> Password: ")
host = input(">> Hostname: ")
os_type = input(">> OS Type, example - cisco_ios, nxos, etc: ")
mac_add = open("mac_data.csv", "r")
print(mac_add.read())

net_driver = get_network_driver(os_type)

#Switch Connection Dict
network_device = {
    "hostname": host,
    "username": user,
    "password": passw
    
}


#Switch Connection
device = net_driver(**network_device)
device.open()

device_mac = device.get_mac_address_table()
print(json.dumps(device_mac, indent=4))


for each_mac in mac_add:
    if mac_add in device_mac_list[n]["mac"]:
        print(f'{device_mac} is connected to {network_device["hostname"]} on {device_mac[n]["interface"]} ')
    else:
        print(f'{device_mac} not found!')
 Output
>> Username: admin
>> Password:
>> Hostname: 172.31.2.2
>> OS Type, example - cisco_ios, nxos, etc: ios
50:00:00:0E:80:02
50:00:00:0B:00:00

[
    {
        "mac": "50:00:00:03:00:02",
        "interface": "Gi0/3",
        "vlan": 2,
        "static": false,
        "active": true,
        "moves": -1,
        "last_move": -1.0
    },
    {
        "mac": "50:00:00:03:00:2F",
        "interface": "Gi0/3",
        "vlan": 2,
        "static": false,
        "active": true,
        "moves": -1,
        "last_move": -1.0
    },
    {
        "mac": "50:00:00:0A:00:00",
        "interface": "Gi1/0",
        "vlan": 2,
        "static": false,
        "active": true,
        "moves": -1,
        "last_move": -1.0
    },
    {
        "mac": "50:00:00:0B:00:00",
        "interface": "Gi0/3",
        "vlan": 2,
        "static": false,
        "active": true,
        "moves": -1,
        "last_move": -1.0
    },
    {
        "mac": "50:00:00:03:00:02",
        "interface": "Gi0/3",
        "vlan": 3,
        "static": false,
        "active": true,
        "moves": -1,
        "last_move": -1.0
    }
]
When you did this:
print(mac_add.read())
You read the enire file. When you get here:
for each_mac in mac_add:
You are already at the end of the file. The loop doesn't run at all.

That really doesn't matter though, because your approach was not going to work anyway.

I think you should get the device mac address table and convert it to a dictionary. It is currently a list of dictionaries.
from napalm import get_network_driver
import getpass


# Make dictionary of networks keyed by mac
network_device = {
    "hostname": input(">> Hostname: "),
    "username": input(">> Username: "),
    "password": getpass.getpass(">> Password: "),
}
net_driver = get_network_driver(input(">> OS Type, example - cisco_ios, nxos, etc: "))
device = net_driver(**network_device)
device.open()
mac_dictionary = {d["mac"]: d for d in device.get_mac_address_table()}


with open("mac_data.csv", "r") as file:
    for mac in file:
        mac = mac.strip()
        if network := mac_dictionary.get(mac):
            print(
                f'{mac} is connected to {network_device["hostname"]} on {network["interface"]} '
            )
        else:
            print(f"{mac} not found!")
Hi Dean

Thanks that worked like a charm. In the below line what are the "d" for?

Sorry for what might be a dumb question but still trying to learn.

Thanks
Ed

mac_dictionary = {d["mac"]: d for d in device.get_mac_address_table()}
That is a dictionary comprehension.
Thank you...one last question Doh

Where does "network" come from in the following line? I don't see it defined anywhere.

if network := mac_dictionary.get(mac):
Thanks
That is where it is defined. := is an assignment operator, like =. The difference is := can be used in an expression.
if network := mac_dictionary.get(mac):
This is the same as:
network = mac_dictionary.get(mac)
if network:
ok I see thanks again!