The purpose of this gist is to gather facts from a network device with Napalm and Nornir alike.
This will help us understand how to use tasks in Nornir.
- We will be using Telnet to connect to our devices. By default, Napalm uses SSH to connect (See Napalm optional args) to the IOS devices. For this reason, we will need to pass
optional_arguments
when instantiating the Napalm driver object. - r2 can be replaced with the device ip. In my case, I was working with host files in my OS.
The following script will connect to one device (r2) and will return its facts. To use telnet, notice we are passing the optional_args
dictionary.
#!/usr/bin/python3.6
from napalm import get_network_driver
from pprint import pprint
driver = get_network_driver('ios')
conn_method = {'transport': 'telnet'}
host = 'r2'
user = 'danielmac'
passwd = 'ccnplab'
# With context manager
with driver(hostname=host, username=user, password=passwd, optional_args=conn_method) as device:
print('Getting facts')
pprint(device.get_facts())
Example Output
{ 'facts': { 'fqdn': 'r2.danielmacuare.com',
'hostname': 'r2',
'interface_list': [ 'Ethernet0/0',
'Ethernet0/1',
'Ethernet0/2',
'Ethernet0/3',
'Ethernet1/0',
'Ethernet1/1',
'Ethernet1/2',
'Ethernet1/3',
'Serial2/0',
'Serial2/1',
'Serial2/2',
'Serial2/3',
'Serial3/0',
'Serial3/1',
'Serial3/2',
'Serial3/3'],
'model': 'Unknown',
'os_version': 'Linux Software (I86BI_LINUX-ADVENTERPRISEK9-M), '
'Version 15.2(2.15)T, ENGINEERING WEEKLY BUILD, '
'synced to V151_4_M3_5',
'serial_number': '2048004',
'uptime': 16680,
'vendor': 'Cisco'}}
Now, to achieve the same with Nornir we will use the open_connection
task. This task allows you to pass optional parameters to Napalm. In our case, we will need to tell Napalm to use telnet as the transport method to connect to the devices.
To do this, we can define a connection_options
dictionary to be used by our host or a group. In my case, since I'm using the Ansible-type inventory, I will define this in the `group_vars/all.yaml' file
You can see HERE an example on how to do this if you are using Nornir's SimpleInventory
inventory instead.
cat ansible/group_vars/all.yaml
---
platform: ios
username: danielmac
password: ccnplab
port: 23
connection_options:
napalm:
extras:
optional_args: {'transport': 'telnet'}
cat nornir_get_facts.py
#!/usr/bin/python3.6
from nornir import InitNornir
from nornir.plugins.tasks.networking import napalm_get
from nornir.plugins.functions.text import print_result
import ipdb
def get_facts_manually(task):
ipdb.set_trace(context=5)
task.host.open_connection("napalm", configuration=task.nornir.config)
r = task.run(napalm_get, getters=['facts'])
task.host.close_connection("napalm")
if __name__ == "__main__":
norn = InitNornir(config_file='config.yaml')
# Working with R2 only.
r2 = norn.filter(hostname='r2')
facts = r2.run(task=get_facts_manually)
print_result(facts)
ipdb is really useful here to inspect the elements that the open_connection will receive. In this case you can make sure you are passing the well know attributes username, password, port.
> /nr_config_gen.py(66)get_facts_manually()
64 def get_facts_manually(task):
65 ipdb.set_trace(context=5)
---> 66 task.host.open_connection("napalm",
67 configuration=task.nornir.config,
68 )
ipdb> task.host.username
'danielmac'
ipdb> task.host.password
'ccnplab'
ipdb> task.host.port
23
ipdb>