■ はじめに
マルチベンダー対応のネットワーク機器制御ライブラリのNAPALMには、ansibleと連携するための napalm-ansible
というモジュール群があります。
今回はその中の napalm_get_facts
というモジュールを利用して Cisco IOS 機器の様々な情報を取得してみます。
GitHub - napalm-automation/napalm-ansibleGitHub - napalm-automation/napalm-ansible
[参考情報(Aristaでの例)]
AnsibleとNAPALMの連携を試してみた – ネットワークエンジニアが日々の出来事を語る
なお、標準モジュールである ios_facts
を利用する場合は、以下の記事をご参照ください。
■ 準備
NAPALM のインストール
あらかじめ NAPALM をインストールします。
pip install napalm
napalm-ansible
モジュール群のダウンロードと配置
git clone https://github.com/napalm-automation/napalm-ansible.git
napalm-automation
ディレクトリ配下の library
ディレクトリを、作成予定の playbook と同じディレクトリに配置します。
■ 基本情報の取得
まず、基本的な情報を取得してみます。
Playbook
以下のようなplaybook を作成します。ansible.cfg
は特に作成していません。
--- - hosts: cisco # イベントリファイルで定義済み gather_facts: no connection: local tasks: - name: get facts from device napalm_get_facts: hostname: "{{ inventory_hostname }}" provider: "{{ cli }}" register: result - name: debug debug: msg: "{{ result }}" vars: cli: # 認証情報 username: "{{ ansible_user }}" # ログインユーザー password: "{{ ansible_password }}" # ログインパスワード dev_os: "ios" # デバイスのOS
なお、napalm_get_facts
モジュールには filter
オプションがあり、情報取得する対象を指定することができます。
デフォルトは facts
となっており、ホスト名やシリアルナンバーなど基本的な情報を取得します。facts
以外については後述します。
実行結果
実行して結果を確認してみます。
[root@localhost ~]# ansible-playbook nf.yml PLAY [cisco] ********************************************************************** TASK [get facts from device] ****************************************************** ok: [x.x.x.x] TASK [debug] ********************************************************************** ok: [x.x.x.x] => { "changed": false, "msg": { "ansible_facts": { "facts": { "fqdn": "csr1.********.com", "hostname": "csr1", "interface_list": [ "GigabitEthernet1", "GigabitEthernet2", "GigabitEthernet3", "GigabitEthernet4" ], "model": "CSR1000V", "os_version": "CSR1000V Software (X86_64_LINUX_IOSD-UNIVERSALK9-M), SOFTWARE (fc3)", "serial_number": "XXXXXXXXXXX", "uptime": 1080, "vendor": "Cisco" } }, "changed": false } } PLAY RECAP ************************************************************************ x.x.x.x : ok=2 changed=0 unreachable=0 failed=0
基本的な情報が取得できました。
■ facts 以外の情報取得方法について
指定できる対象
前述のように filter
オプションでは情報取得する対象を指定することができます。
指定できるものは Cisco IOS の場合は以下の通りです。
- arp_table
- bgp_neighbors
- config
- environment
- facts
- interfaces
- interfaces_counters
- interfaces_ip
- lldp_neighbors
- lldp_neighbors_detail
- mac_address_table
- ntp_servers
- ntp_stats
- optics
- snmp_information
指定できる値は、napalm-automation
自身のドキュメントには記述されいませんが、
NAPALM本体の「Getters support matrix」のIOS(今回の場合)の列を見ると分かります。
Supported Devices — NAPALM 1 documentation
例)
get_config に対応していれば filter
に config
が指定でき、以下のように記述できる。
napalm_get_facts: hostname: "{{ inventory_hostname }}" provider: "{{ cli }}" filter: - "config"
それぞれどのように取得できるのか試します。 ※あまり設定が入っていない機器で試したので情報が少ないです。
arp_table
今回の環境では特に通信していないため空となりました。
"arp_table": []
bgp_neighbors
今回の環境ではBGPは未設定のため空となりました。
"bgp_neighbors": {}
config
running-config
が取得できました。
"config": { "candidate": "", "running": "Building configuration...\n\nCurrent configuration : 39iguration change at 11:25:09 UTC Sat May 27 2017\n!\nversion 16.3\n(略) }
environment
ハードウェア状況の情報が取得できました。
"environment": { "cpu": { "0": { "%usage": 0.0 } }, "fans": { "invalid": { "status": true } }, "memory": { "available_ram": 1765843468, "used_ram": 333704364 }, "power": { "invalid": { "capacity": -1.0, "output": -1.0, "status": true } }, "temperature": { "invalid": { "is_alert": false, "is_critical": false, "temperature": -1.0 } } }
facts
再掲になりますが、ホスト名やシリアルナンバーなどの基本的な情報が取得できました。
"facts": { "fqdn": "csr1.********.com", "hostname": "csr1", "interface_list": [ "GigabitEthernet1", "GigabitEthernet2", "GigabitEthernet3", "GigabitEthernet4" ], "model": "CSR1000V", "os_version": "CSR1000V Software (X86_64_LINUX_IOSD-UNIVERSALK9-M), SOFTWARE (fc3)", "serial_number": "XXXXXXXXXXX", "uptime": 1200, "vendor": "Cisco" }
interfaces
インターフェース情報が取得できました。
"interfaces": { "GigabitEthernet1": { "description": "N/A", "is_enabled": true, "is_up": true, "last_flapped": -1.0, "mac_address": "2C:C2:60:XX:XX:XX", "speed": 1000 }, "GigabitEthernet2": { "description": "N/A", "is_enabled": true, "is_up": true, "last_flapped": -1.0, "mac_address": "2C:C2:60:XX:XX:XX", "speed": 1000 }, "GigabitEthernet3": { "description": "N/A", "is_enabled": true, "is_up": true, "last_flapped": -1.0, "mac_address": "2C:C2:60:XX:XX:XX", "speed": 1000 }, "GigabitEthernet4": { "description": "N/A", "is_enabled": true, "is_up": true, "last_flapped": -1.0, "mac_address": "2C:C2:60:XX:XX:XX", "speed": 1000 } }
interfaces_counters
インターフェースのカウンタ情報が取得できました。
"interfaces_counters": { "GigabitEthernet1": { "rx_broadcast_packets": 0, "rx_discards": 0, "rx_errors": 753, "rx_multicast_packets": 0, "rx_octets": 68538, "rx_unicast_packets": 980, "tx_broadcast_packets": -1, "tx_discards": 0, "tx_errors": 0, "tx_multicast_packets": -1, "tx_octets": 199698, "tx_unicast_packets": 1358 }, (省略) } }
interfaces_ip
IPアドレスが設定されているインターフェースの情報が取得できました。
"interfaces_ip": { "GigabitEthernet1": { "ipv4": { "10.0.0.51": { "prefix_length": 24 } } } }
lldp_neighbors
今回の環境では未設定のため空となりました。
"lldp_neighbors": {}
lldp_neighbors_detail
今回の環境では未設定のため空となりました。
"lldp_neighbors_detail": {}
mac_address_table
今回の環境では未通信のため空となりました。
"mac_address_table": []
ntp_servers
今回の環境では未設定のため空となりました。
"ntp_servers": {}
ntp_stats
今回の環境では未設定のため空となりました。
"ntp_stats": []
optics
今回の環境ではSFP等のスロットはないため空となりました。
"optics": {}
snmp_information
今回の環境では未設定のため特に意味のない値となりました。
"snmp_information": { "chassis_id": "%SNMP agent not enabled", "community": {}, "contact": "unknown", "location": "unknown" }
■ さいごに
稼働中のネットワーク機器の情報を収集したいケースは割とよくあると思いますが、自作しなくてもここまでできますので、もし、取得したい情報がこのモジュールで取得できるのであれば、利用してみるのもよいのではないでしょうか。
なお、Ansible を利用せずに、pythonスクリプト中でなるべくパース処理の手間を省きたい場合は、TextFSMというライブラリと ntc-template というテンプレート集を利用するのが良いと思います。 github.com github.com