"pause" 每台主机
"pause" for every host
在滚动更新之前,我想在我们的监控工具中为每台主机设置停机时间。我为此创建了一个自定义模块。设置停机时间时可能会出现问题,我们无法解决。在那种情况下,我想让用户选择是否应中止部署或继续部署而不设置停机时间。
假设我这样调用我的模块:
- downtime:
duration: 5m
comment: whatever
ignore_errors: true
register: downtime
所以我忽略了错误以便能够继续。否则设置停机失败的主机将不会被进一步处理。
在下一步中,我希望用户手动确认他是否要为每个没有设置停机时间的主机继续。
- name: Request user confirmation to proceed in case downtime could not be set
pause:
prompt: 'Downtime could not be set for all hosts. Do you want to proceed? Press return to continue. Press Ctrl+c and then "a" to abort'
when: "{{ downtime | failed }}"
不幸的是,pause
模块(实际上它是一个动作插件)只会在第一个被处理的主机上暂停。因此,如果第一台主机失败,它将暂停,如果第一台主机通过而所有其他主机失败,它将继续处理所有主机。
这似乎是预期的行为。来自 docs:
The pause module integrates into async/parallelized playbooks without any special considerations (see also: Rolling Updates). When using pauses with the serial
playbook parameter (as in rolling updates) you are only prompted once for the current group of hosts.
所以无论如何,即使我会使用 serial: 1
(在这种情况下这是不可能的)暂停也只会为第一台主机停止。
现在我只是无条件地暂停,让用户决定是否要继续,无论停机任务是否失败。但由于失败应该非常罕见,这是我想避免的手动步骤。
谁能看到解决方法:
- 暂停每个 主机(失败)
- 暂停一次,以防任何主机失败
This bug report 给了我使用循环的灵感。以下解决方案要求分别确认每个失败的主机:
- downtime:
duration: 5m
comment: whatever
ignore_errors: true
register: downtime
- name: Saving downtime state
set_fact:
downtime_failed: "{{ downtime | failed }}"
- name: Request user confirmation to proceed in case downtime could not be set
pause:
prompt: 'Downtime could not be set for {{ item }}. Do you want to proceed? Press return to continue. Press Ctrl+c and then "a" to abort'
when: "{{ hostvars[item]['downtime_failed'] }}"
with_items: "{{ play_hosts }}"
由于 pause
模块仅 运行 用于清单中列出的第一台主机,我们遍历所有可用主机 (play_hosts
)。要从所有其他主机访问状态,我们首先需要将结果存储为事实 (set_fact
),然后我们可以通过 hostvars
访问它,它包含当前播放的所有主机的所有事实。
为了运行一组主机上的pause
模块,我做了这个技巧:
- pause:
prompt: "{{ item }} will be restarted. Enter 'YES' to restart"
register: input
with_items: "{{ play_hosts }}"
- set_fact:
user_input: "{{ item.user_input }}"
with_items: "{{ hostvars[play_hosts.0].input.results }}"
when: item.item == ansible_hostname|upper
正如udondan所说,pause
模块运行在组的第一台主机上。通过这两项任务,我们获得每个主机的输入并为所有主机设置一个可用的新事实。
在滚动更新之前,我想在我们的监控工具中为每台主机设置停机时间。我为此创建了一个自定义模块。设置停机时间时可能会出现问题,我们无法解决。在那种情况下,我想让用户选择是否应中止部署或继续部署而不设置停机时间。
假设我这样调用我的模块:
- downtime:
duration: 5m
comment: whatever
ignore_errors: true
register: downtime
所以我忽略了错误以便能够继续。否则设置停机失败的主机将不会被进一步处理。
在下一步中,我希望用户手动确认他是否要为每个没有设置停机时间的主机继续。
- name: Request user confirmation to proceed in case downtime could not be set
pause:
prompt: 'Downtime could not be set for all hosts. Do you want to proceed? Press return to continue. Press Ctrl+c and then "a" to abort'
when: "{{ downtime | failed }}"
不幸的是,pause
模块(实际上它是一个动作插件)只会在第一个被处理的主机上暂停。因此,如果第一台主机失败,它将暂停,如果第一台主机通过而所有其他主机失败,它将继续处理所有主机。
这似乎是预期的行为。来自 docs:
The pause module integrates into async/parallelized playbooks without any special considerations (see also: Rolling Updates). When using pauses with the
serial
playbook parameter (as in rolling updates) you are only prompted once for the current group of hosts.
所以无论如何,即使我会使用 serial: 1
(在这种情况下这是不可能的)暂停也只会为第一台主机停止。
现在我只是无条件地暂停,让用户决定是否要继续,无论停机任务是否失败。但由于失败应该非常罕见,这是我想避免的手动步骤。
谁能看到解决方法:
- 暂停每个 主机(失败)
- 暂停一次,以防任何主机失败
This bug report 给了我使用循环的灵感。以下解决方案要求分别确认每个失败的主机:
- downtime:
duration: 5m
comment: whatever
ignore_errors: true
register: downtime
- name: Saving downtime state
set_fact:
downtime_failed: "{{ downtime | failed }}"
- name: Request user confirmation to proceed in case downtime could not be set
pause:
prompt: 'Downtime could not be set for {{ item }}. Do you want to proceed? Press return to continue. Press Ctrl+c and then "a" to abort'
when: "{{ hostvars[item]['downtime_failed'] }}"
with_items: "{{ play_hosts }}"
由于 pause
模块仅 运行 用于清单中列出的第一台主机,我们遍历所有可用主机 (play_hosts
)。要从所有其他主机访问状态,我们首先需要将结果存储为事实 (set_fact
),然后我们可以通过 hostvars
访问它,它包含当前播放的所有主机的所有事实。
为了运行一组主机上的pause
模块,我做了这个技巧:
- pause:
prompt: "{{ item }} will be restarted. Enter 'YES' to restart"
register: input
with_items: "{{ play_hosts }}"
- set_fact:
user_input: "{{ item.user_input }}"
with_items: "{{ hostvars[play_hosts.0].input.results }}"
when: item.item == ansible_hostname|upper
正如udondan所说,pause
模块运行在组的第一台主机上。通过这两项任务,我们获得每个主机的输入并为所有主机设置一个可用的新事实。