■ はじめに
Ansible 2.7 で、ターゲットホストに到達不能の状態を無視する ignore_unreachable
キーワードが追加されました。
changelog
New keyword ignore_unreachable for plays and blocks. Allows ignoring tasks that fail due to unreachable hosts, and check results with is unreachable test.
言葉では少し説明しにくいので、試した結果を紹介します。
■ 構成
以下のように、 Ansibleから到達できるホストとできないホストを想定して試します。
ホスト |
OS |
Ansible からの到達性 |
testsv1 |
linux |
○:可 |
testsv99 |
linux |
×:不可 |
■ 基本 Playbook
2つのタスクがあり、1つめの yum モジュールでは、あえて存在しないパッケージ名を指定して エラーが発生するようにしてます。
- hosts: linux
gather_facts: no
tasks:
- name: yum error
yum:
name: invalid_package_xxx
- name: debug
debug:
msg: "Hello debug."
この Playook を基本として、ignore_unreachable
を指定を変えて試してみます。
■ ignore_unreachable: no
(デフォルト)の場合
- hosts: linux
gather_facts: no
tasks:
- name: yum error
yum:
name: invalid_package_xxx
ignore_unreachable: no
- name: debug
debug:
msg: "Hello debug."
$ ansible-playbook -i inventory iu_linux.yml
PLAY [linux] ********************************************************************
TASK [yum error] ****************************************************************
fatal: [testsv1]: FAILED! => {"ansible_facts": {"pkg_mgr": "yum"}, "changed": false, "msg": "No package matching 'invalid_package_xxx' found available, installedor updated", "rc": 126, "results": ["No package matching 'invalid_package_xxx' found available, installed or updated"]}
fatal: [testsv99]: UNREACHABLE! => {"changed": false, "msg": "Failed to connect to the host via ssh: ssh: connect to host 172.16.0.11 port 22: No route to host\r\n", "unreachable": true}
to retry, use: --limit @/vagrant/a27/iu_linux.retry
PLAY RECAP **********************************************************************
testsv1 : ok=0 changed=0 unreachable=0 failed=1
testsv99 : ok=0 changed=0 unreachable=1 failed=0
testsv1
では、1つめの yum モジュールのタスクでエラーが発生したためしたが、処理が中断されます。
一方、testsv99
では、1つめのタスクの時点で unreachable
なので、処理が中断されます。
これがデフォルトの動作です。
このように、2つめのタスクが実行されなかった点では testsv1 も teest99 も同じですが、理由が異なります。
■ ignore_unreachable: yes
の場合
次に、ignore_unreachable: yes
に変更した Playbook を用意します、
- Playbook
- hosts: linux
gather_facts: no
tasks:
- name: yum error
yum:
name: invalid_package_xxx
ignore_unreachable: yes
- name: debug
debug:
msg: "Hello debug."
$ ansible-playbook -i inventory iu_linux.yml
PLAY [linux] ********************************************************************
TASK [yum error] ****************************************************************
fatal: [testsv99]: UNREACHABLE! => {"changed": false, "msg": "Failed to connect to the host via ssh: ssh: connect to host 172.16.0.11 port 22: No route to host\r\n", "skip_reason": "Host testsv99 is unreachable", "unreachable": true}
fatal: [testsv1]: FAILED! => {"ansible_facts": {"pkg_mgr": "yum"}, "changed": false, "msg": "No package matching 'invalid_package_xxx' found available, installedor updated", "rc": 126, "results": ["No package matching 'invalid_package_xxx' found available, installed or updated"]}
TASK [debug] ********************************************************************
ok: [testsv99] => {
"msg": "Hello debug."
}
to retry, use: --limit @/vagrant/a27/iu_linux.retry
PLAY RECAP **********************************************************************
testsv1 : ok=0 changed=0 unreachable=0 failed=1
testsv99 : ok=1 changed=0 unreachable=1 failed=0
先ほどと異なる点は、2つめの dubug モジュールのタスクが実行されるかどうかです。
testsv1
では、1つめの yum モジュールのタスクでエラーが発生したためしたが、処理が中断されます。
一方、testsv99
では、1つめのタスクの時点で unreachable
です。ただし、ignore_unreachable: yes
が指定されているので、2つめの debug モジュールのタスクが実行されました。
■ おまけ ignore_errors: yes
の場合
比較をするため、Ansible 2.6 までにもあった、似たようなオプション ignore_errors: yes
でも試します。
- hosts: linux
gather_facts: no
tasks:
- name: yum error
yum:
name: invalid_package_xxx
ignore_errors: yes
- name: debug
debug:
msg: "Hello debug."
$ ansible-playbook -i inventory iu_linux.yml
PLAY [linux] ********************************************************************
TASK [yum error] ****************************************************************
fatal: [testsv1]: FAILED! => {"ansible_facts": {"pkg_mgr": "yum"}, "changed": false, "msg": "No package matching 'invalid_package_xxx' found available, installedor updated", "rc": 126, "results": ["No package matching 'invalid_package_xxx' found available, installed or updated"]}
...ignoring
fatal: [testsv99]: UNREACHABLE! => {"changed": false, "msg": "Failed to connect to the host via ssh: ssh: connect to host 172.16.0.11 port 22: No route to host\r\n", "unreachable": true}
TASK [debug] ********************************************************************
ok: [testsv1] => {
"msg": "Hello debug."
}
to retry, use: --limit @/vagrant/a27/iu_linux.retry
PLAY RECAP **********************************************************************
testsv1 : ok=2 changed=0 unreachable=0 failed=0
testsv99 : ok=0 changed=0 unreachable=1 failed=0
testsv1
では、1つめの yum モジュールのタスクでエラーが発生しましたが、 ignore_error: yes
のため、無視して2つめの debug モジュールのタスクが実行されました。
一方、testsv99
では、1つめのタスクの時点で unreachable
なので、その時点で処理が終わっています。
■ 補足
ignore_unreachable
を指定できる箇所
公式ドキュメントの Playbook Keywords によると、Play、Role、Block、Task のいずれにも指定できるようです。
例えば、Play に指定する場合はこのようになります。
- hosts: linux
gather_facts: no
ignore_unreachable: yes
tasks:
...(略)...
利用できるコネクションプラグイン
試した限り、network_cli
や netconf
といったネットワークモジュール向けのコネクションプラグインでは、ignore_unreachable
の指定が効かなかっです。
■ さいごに
ignore_unreachable
、ignore_errors
についてまとめると以下のようになります。
ignore_unreachable |
ignore_errors |
到達不能の場合 |
到達可能だが、モジュール実行エラーの場合 |
no (デフォルト) |
no (デフォルト) |
中断 |
中断 |
yes |
no (デフォルト) |
無視して継続 |
中断 |
yes |
yes |
無視して継続 |
無視して継続 |
no (デフォルト) |
yes |
中断 |
無視して継続 |
ignore_unreachable: yes
を指定する必要がるケースは限定的かもしれませんが、何かのときに思い出していただければ幸いです。