netmiko で Cisco IOS へログインするサンプル
netmiko を使って Cisco IOS デバイスへログインするサンプルをメモしておきます。 TELNET / SSH アクセスする対象には CML2 上の IOSv 15.9(3)M3 を利用しました。
netmiko のインストール
今回は venv 環境を作成し、そこに netmiko をインストールすることにしました。 まず venv 環境を作成します。
| mkdir my-first-netmiko
cd my-first-netmiko
python3 -m venv venv
source venv/bin/activate
|
netmiko をインストールします。
| python3 -m pip install netmiko
|
TELNET
TELNET するサンプルは以下の通りです。 TELNET する場合、device_type
には cisco_ios_telnet
を指定します (cisco_ios
を指定すると TELNET では無く、SSH 接続しようとするので注意が必要です)。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios_telnet",
"ip": "10.0.0.1",
"username": "admin",
"password": "password",
"port": 23,
"secret": "secret",
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
output = net_connect.send_command("show clock")
print(output)
net_connect.disconnect()
|
SSH (パスワード認証)
パスワード認証による SSH 接続のサンプルは以下の通りです。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios",
"ip": "10.0.0.1",
"username": "admin",
"password": "password",
"port": 22,
"secret": "secret",
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
output = net_connect.send_command("show clock")
print(output)
net_connect.disconnect()
|
SSH (鍵認証)
鍵認証による SSH 接続のサンプルは以下の通りです。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios",
"ip": "10.0.0.1",
"username": "admin",
"key_file": "~/.ssh/id_rsa",
"port": 22,
"secret": "secret",
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
output = net_connect.send_command("show clock")
print(output)
net_connect.disconnect()
|
設定変更
設定変更を行う場合は send_command
を多用するのでは無く、send_config_set
を利用することで簡単に設定変更出来ます。 send_config_set
を使えば設定モードへの移行 (例えば configure termina
) や、設定モードの解除なども自動的に実行してくれます。 以下の例では send_config_set
を使いつつ、設定変更した内容を標準出力へ書き出しています。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios",
"ip": "10.0.0.1",
"username": "admin",
"password": "password",
"port": 22,
"secret": "secret",
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
commands = [
"interface GigabitEthernet0/1",
"description TEST",
" ip address 192.0.2.1 255.255.255.0",
" no shutdown",
]
output = net_connect.send_config_set(commands)
print(output)
net_connect.disconnect()
|
show tech-support
show tech-support
を実行する、以下のサンプルを用意したとします。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios",
"ip": "10.0.0.1",
"username": "admin",
"password": "password",
"port": 22,
"secret": "secret",
"fast_cli": False
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
output = net_connect.send_command("show tech-support")
print(output)
net_connect.disconnect()
|
しかし、これを実行すると今回の環境では以下のエラーになりました。
| # ./5-show-tech-support.py
Traceback (most recent call last):
File "/root/my-first-netmiko/./5-show-tech-support.py", line 19, in <module>
output = net_connect.send_command("show tech-support")
File "/root/my-first-netmiko/venv/lib/python3.9/site-packages/netmiko/utilities.py", line 500, in wrapper_decorator
return func(self, *args, **kwargs)
File "/root/my-first-netmiko/venv/lib/python3.9/site-packages/netmiko/base_connection.py", line 1535, in send_command
raise IOError(
OSError: Search pattern never detected in send_command: IOSv\#
|
send_command
を実行した場合のタイムアウト時間はデフォルトで 100 秒です。 fast_cli
というパラメータはデフォルトで True
ですが、これが True
だと各種タイムアウト値が 0.1 倍されます。 今回の CML2 環境では show tech-support
が完了するまでに 30 秒程度かかっているのですが、netmiko のタイムアウト値が 100 x 0.1 = 10 秒になっており、send_command
が期待した文字列 (ホスト名) が返ってこない=タイムアウトしたと判断し、結果的に OSError: Search pattern never detected in send_command: IOSv
エラーになっています。 この問題を解決するには以下のように fast_cli
を False
に設定します。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23 | #!/usr/bin/env python3
from netmiko import ConnectHandler
cisco_ios = {
"device_type": "cisco_ios",
"ip": "10.0.0.1",
"username": "admin",
"password": "password",
"port": 22,
"secret": "secret",
"fast_cli": False
}
net_connect = ConnectHandler(**cisco_ios)
net_connect.enable()
net_connect.send_command("terminal length 0")
output = net_connect.send_command("show tech-support")
print(output)
net_connect.disconnect()
|
今回は fast_cli
を False
に設定することで show tech-support
を実行出来ましたが、更にタイムアウト時間を調整する必要がある場合は send_command
の引数に delay_factor
を設定し、タイムアウト値に係数を掛けるなど、追加の考慮を検討しなければならないケースもあるかもしれません。
参考
IOSv のコンフィグ
今回、CML2 上に作成した IOSv には以下を設定しました。 PUBLIC-KEY
やアドレス、ルーティング設定などは自身の環境にあわせて差し替えます。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38 | hostname IOSv
!
service timestamps debug datetime msec localtime
service timestamps log datetime msec localtime
!
enable secret secret
!
clock timezone JST +9
!
no ip domain-lookup
ip domain name example.local
!
aaa new-model
username admin password password
!
interface GigabitEthernet0/0
ip address 10.0.0.1 255.255.255.0
no shutdown
!
ip route 0.0.0.0 0.0.0.0 10.0.0.254
!
ip ssh version 2
ip ssh pubkey-chain
username admin
key-string
(PUBLIC-KEY)
exit
!
no banner exec ^C
no banner incoming ^C
no banner login ^C
!
line vty 0 4
transport input all
!
crypto key generate rsa modulus 2048
!
end
|