我正在使用 ansible 来升级网络设备的软件。安装后,我重新启动盒子,然后使用 ansible 的wait_for模块等待 SSH 恢复,然后使用 do-until 循环运行命令并等待特定的输出字符串:
- name: Wait for box to come back up
local_action: wait_for host={{ ansible_ssh_host | default(inventory_hostname) }}
search_regex=OpenSSH
port=22
delay=20
timeout=600
- name: Wait for box to enter the running phase
shell: tmsh -q -a show sys mcp
changed_when: False
ignore_errors: True
register: mcp_wait
until: mcp_wait.stdout.find("running") != -1
retries: 1200
delay: 10
Run Code Online (Sandbox Code Playgroud)
问题是,对于某些软件升级,设备将重新启动两次。它出现,SSH 启动,然后安装一些固件更新,并第二次重新启动。这导致我的剧本出错。任务wait_for成功,然后 do-until 任务开始循环,但盒子的第二次重新启动会导致此 do-until 命令失败并出现错误SSH Connection timed out。
TASK: [appliance | Wait for box to come back up] *******************************
<127.0.0.1> REMOTE_MODULE wait_for host=10.1.1.1 search_regex=OpenSSH port=22 delay=20 timeout=600
ok: [10.1.1.1 -> 127.0.0.1] => {"changed": false, "elapsed": 93, "path": null, "port": 22, "search_regex": "OpenSSH", "state": "started"}
TASK: [appliance | Wait for box to enter the running phase] ***********************************
<10.1.1.1> REMOTE_MODULE command tmsh -q -a show sys mcp #USE_SHELL
Result from run 1 is: {'cmd': 'tmsh -q -a show sys mcp', 'end': '2015-10-01 10:58:27.025674', 'stdout': u'', 'changed': True, 'attempts': 1, 'start': '2015-10-01 10:58:26.928485', 'delta': '0:00:00.097189', 'stderr': 'Cannot connect to mcpd.', 'rc': 1, 'warnings': []}
--snipped repeated lines--
<10.1.1.1> REMOTE_MODULE command tmsh -q -a show sys mcp #USE_SHELL
fatal: [10.1.1.1] => SSH Error: ssh: connect to host 10.1.1.1 port 22: Connection timed out
while connecting to 10.1.1.1:22
It is sometimes useful to re-run the command using -vvvv, which prints SSH debug output to help diagnose the issue.
FATAL: all hosts have already failed -- aborting
PLAY RECAP ********************************************************************
to retry, use: --limit @/home/loudsong/play.retry
10.1.1.1 : ok=25 changed=4 unreachable=1 failed=0
Run Code Online (Sandbox Code Playgroud)
所以我真正需要的是保持我的任务Wait for box to enter the running phase循环直到它最终成功,无论目标设备是否完全无法访问。wait_for如果我能够捕获 SSH 连接错误,然后执行另一个任务来等待盒子完成第二个重新启动周期,我也会很高兴。有人有什么建议吗?
我最终得到的解决方案是将操作转换为本地操作:
- name: Wait till MCP enters the running phase
local_action: command sshpass -p "{{ansible_ssh_pass|default('')}}" ssh root@{{inventory_hostname}} tmsh -q -a show sys mcp
changed_when: False
register: mcp_wait
until: mcp_wait.stdout.find("running") != -1
retries: 300
Run Code Online (Sandbox Code Playgroud)
这样,任务将继续循环,尝试通过 SSH 远程执行命令,直到在 stdout 中发现“正在运行”,即使该框无法访问。
顺便说一句,我确实看到 Ansible 允许您编写回调,这似乎可以让您捕获“无法访问”的事件。尽管我没有对此进行足够的追求,以确保它能够解决我在问题中描述的问题。请参阅函数 v2_runner_on_unreachable(): https://github.com/ansible/ansible/blob/devel/lib/ansible/plugins/callback/default.py
| 归档时间: |
|
| 查看次数: |
3492 次 |
| 最近记录: |