【telnetでHŞRPプライオリティ変更】
---telnetモジュールでNW自動化の設定---
Ansibleの特徴の一つに「エージェントレスである」と言われる。。
他の自動化ツール、例えばChefやPuppetと比べて、設定対象側にエージェントソフトをインストールする必要がなく
SSHで接続する条件さえ満たせば他に追加の設定は無い、ということらしい。
しかしすぐにはsshを有効にできないとか、もともと管理対象側にsshの機能がないという環境は現状まだあると思う。特にNWインフラ系。
今回は、sshが使えない場合の暫定的な対応を想定して、Ansibleのtelnetモジュールを使ってCisco機の工事手順の一部を作成してみた。
<<HSRPプライオリティ変更>>
-
例として以下のエクセルの手順書の工事を自動化することを想定
telnetモジュールを使ってこの工事手順を自動化するために作ったplaybookと実行シーケンス
playbookを4回実行してやっと完了する手順になった。
切戻工程はパラメータを少し変えて使いまわせる。が、実行順序の確認や編集のための手間が多く、煩雑。
実行順序はjenkinsやAnsibleTowerなどのトリガー機能で連動させるかな。
以下にA、B、DのplaybookとF,Gのインべントリーファイルを記載。
<<Playbook.A>>
--- - hosts: cisco connection: local gather_facts: False tasks: - name: pre check telnet: user: "{{user}}" password: "{{pass}}" login_prompt: "Username: " prompts: - "[>|#]|Password: " command: - terminal length 0 - enable - "{{enpass}}" - "show standby Vlan{{vlan}}" - "show run interface Vlan{{vlan}}" changed_when: False register: command_result_pre failed_when: '"State is Standby" in "command_result_pre"' - name: pre debug debug: var: command_result_pre.output - name: pre log export local_action: module: copy dest: "{{log_dir}}/{{inventory_hostname}}.log" backup: yes content: "{{ command_result_pre.output}}" changed_when: False
<<inventory.F>>
telnetcisco
[cisco] ciscoR1 ansible_host=192.168.3.215 vlan="951" hsrp_grnum="6" #ciscoR3 ansible_host=192.168.3.3 vlan="952" hsrp_grnum="7" #ciscoR5 ansible_host=192.168.3.19 vlan="953" hsrp_grnum="8" #ciscoR7 ansible_host=192.168.3.35 vlan="954" hsrp_grnum="9" [cisco:vars] user="hoge" pass="1234" enpass="1234" log_dir="/home/ktn/telnetlog" ansible_become=yes ansible_become_method=enable #hsrp_pri="80" hsrp_pri="120"
<<Playbook.B>>
cent_hsrp_actchk.yml
--- - hosts: localhost gather_facts: no connection: local tasks: - name: check status shell: "cat /home/ktn/telnetlog/{{hostfile}}.log" register: check_status failed_when: "'item ' not in check_status.stdout" with_items: - "Active router is local" - "standby {{hsrp_grnum}} priority {{act_pri}}" - "Standby router is {{peeradd}}" changed_when: False
<<inventory.G>>
telnetcent
[cent] localhost ansible_host=192.168.3.218 [cent:vars] ansible_ssh_user=hoge ansible_ssh_pass=1234 ansible_port=22 hostfile="ciscoR1" vlan="951" hsrp_grnum="6" act_pri="120" sby_pri="80" peeradd="10.100.14.194" log_dir="/home/ktn/telnetlog"
<<Playbook.D>>
--- - hosts: cisco connection: local gather_facts: False tasks: - name: configuer telnet telnet: user: "{{user}}" password: "{{pass}}" login_prompt: "Username: " prompts: - "[>|#]|Password: " command: - terminal length 0 - enable - "{{enpass}}" - "conf t" - "int Vlan{{vlan}}" - "standby {{hsrp_grnum}} priority 120" changed_when: False register: command_result - name: configurer debug debug: var: command_result.output - name: pause pause: seconds: 15 - name: after telnet telnet: user: "{{user}}" password: "{{pass}}" login_prompt: "Username: " prompts: - "[>|#]|Password: " command: - terminal length 0 - enable - "{{enpass}}" - "show standby Vlan{{vlan}}" - "show run interface Vlan{{vlan}}" changed_when: False register: command_result_after - name: debug_after debug: var: command_result_after.output - name: log export_after local_action: module: copy dest: "{{log_dir}}/{{inventory_hostname}}.log" backup: yes content: "{{ command_result_after.output}}" changed_when: False
<<確認>>
- 特権モードに移行しcisco機器への設定が可能なこと
- telnetモジュールで冪等性の担保ができるか
- telnet接続とssh接続で利用できるモジュール機能の違いをいくつか実装してみて確認する。実行ログが指定のディレクトリに出力されるかどうか
pause
が使えるかwait_for
、when
が使えるか/等
<<結果と課題>>
- telnetモジュールでは、
command
で実際のコマンドをリストで記載しvtyで投入していくだけの動作となり冪等性は担保されない。変更前確認⇒変更⇒変更後確認の都度に確認するための仕組みが必要。 - sshでは利用できていた多くのサブモジュールが機能しない。例えば、コマンド出力の応答文字列を
wait_for
、when
を使ってyamlで条件判断させたかったが認識しなかった。 - hsrpのpreempt delayを待つために
pause
を入る場合、telnetモジュール対してグローバルにpause
指定できるが、コマンド毎には指定できない。
<<現状の暫定対応>>
- 変更前確認コマンド投入⇒ファイル比較⇒変更コマンド投入⇒変更前確認コマンド投入⇒ファイル比較、、、という風にplaybookをに分けて、確認工程は
local_action
モジュールでファイルをコントローラに保存し、コントローラ側のcommand
やshell
モジュールを使って比較する方法で対応することにした。
<<思ったこと>>
- telnetモジュールでは使える機能がかなり限定されるため、自動化手順の実装の工程が多く複雑になる。telnetモジュールを無理やり使うくらいならこれま通りteratermマクロとシェルスクリプトでいいやっと思った。公式ドキュメントでもtelnetモジュールは主にsshを有効にするための手段として使われる、、、とあるように、可能な限りSSHを有効化にシフトして行くのが良い。次回は、ssh有効化するためのtelnetモジュールを作成し、sshを使う方式を恒久対応とする予定。
*1:パラメータはすべてサンプル値です