Orange的运维学习日记–47.Ansible进阶之异步处理
文章目录
- Orange的运维学习日记--47.Ansible进阶之异步处理
- Playbook 执行顺序原理
- 可选执行策略
- 调整并发连接数:forks 参数
- 查看与修改 forks
- 性能调优建议
- 分批执行全局任务:serial 关键字
- serial 用法示例
- 应用场景与注意
- 异步任务与后台执行:async 与 poll
- 异步示例
- 后台任务跟踪:async_status
- 状态检测:wait_for 模块
- 文件存在检测
- TCP 端口检测
- 实践建议与最佳实践
Playbook 执行顺序原理
当 Ansible 运行 playbook 时 会按 playbook 中定义的 play 顺序依次执行
每个 play 里 对所有目标主机按批次完成一个任务后 再统一进入下一个任务
该行为源自默认的 linear 策略 旨在保持任务执行流程可预期
在执行过程中
- Ansible 控制节点会对 hosts 列表建立 SSH 连接池
- 按照 forks 配置 对一批主机同时发起任务
- 等所有批次完成当前任务后 才会调度下一个任务
- 直到所有任务在所有主机上执行完毕 后释放连接
该模型在少量主机时表现稳定 可充分利用并发优势
当管理数百甚至上千台主机时 过多并发会对控制节点产生显著负载
可选执行策略
Ansible 支持多种执行策略
- linear(默认) 按照上文所述批次执行
- free 在单个主机执行完任务后 立即执行下一个任务 无需等待其他主机
- debug 用于调试 playbook 记录详细执行信息
选择不同策略 会对批量运维场景带来灵活度与安全性的平衡
调整并发连接数:forks 参数
forks 定义 Ansible 在同一时刻可并行启动的 SSH 连接数
默认值较低 为 5 以避免对控制节点和目标节点造成过大压力
查看与修改 forks
在命令行中可查询当前值
ansible-config dump | grep DEFAULT_FORKS
在 ansible.cfg 中修改后生效
[defaults]
forks = 20
也可在执行 playbook 时通过 -f
或 --forks
覆盖
ansible-playbook playbook.yaml --forks 10
性能调优建议
- 管理大量 Linux 主机时 模块大多在目标主机执行 控制节点压力小 可适当提高 forks(如 50~100)
- 管理网络设备或其它非 Linux 设备时 模块执行更依赖控制节点 需谨慎提升 forks 防止 CPU 或内存瓶颈
- 可结合监控工具 实时观察控制节点负载 并根据实际情况动态调整
分批执行全局任务:serial 关键字
serial 可对整个 play 进行批量拆分 先让部分主机完成 play 中所有任务 再依次切换到下一批
常见场景包括滚动升级 Web 集群 或在高可用环境中进行安全补丁更新
serial 用法示例
将所有主机分成两台一组 执行完整部署流程
---
- name: Rolling update of httpdhosts: webserversserial: 2tasks:- name: install latest httpdyum:name: httpdstate: latestnotify: restart httpdhandlers:- name: restart httpdservice:name: httpdstate: restarted
也可使用百分比表示 批次大小根据主机总数自动计算 最小为 1
serial: 25%
应用场景与注意
- 在批量下线或升级时 避免所有实例同时不可用
- 可与 health check 脚本结合 在每批次完成后 验证服务可用性
- 任务失败时 可快速定位问题所在批次 便于回滚或重试
异步任务与后台执行:async 与 poll
默认情况下 Ansible 会等待单个任务完成后 再调度下一个任务
对耗时操作 如大文件下载、数据库备份、重启服务 等 同步等待会严重拖慢 playbook 整体执行速度
通过 async 和 poll 实现异步执行
- async 指任务最长执行时间(秒) 超时会被强制终止
- poll 指检查任务状态的间隔(秒) poll: 0 则不等待 立即继续后续任务
异步示例
将下载任务放入后台 不阻塞后续执行
---
- name: download ISO in backgroundhosts: node1tasks:- name: fetch CentOS ISOget_url:url: http://example.com/CentOS.isodest: /home/centosasync: 600poll: 0- name: immediately start next taskdebug:msg: move on without waiting download
当 async 小于实际运行时间 时 会在超时后报错
async: 5
poll: 2
此时若命令需 10 秒 执行将被中断
后台任务跟踪:async_status
Fire-and-forget 模式需借助 async_status 模块跟踪完成状态
---
- name: start long taskhosts: node1tasks:- shell: sleep 30async: 60poll: 0register: job- name: wait for async task to finishasync_status:jid: "{{ job.ansible_job_id }}"register: job_resultuntil: job_result.finishedretries: 10delay: 5
结合 retries 和 delay 可控制最大等待时长 与检查频率
状态检测:wait_for 模块
当异步操作与外部条件挂钩时 可使用 wait_for 模块对文件、端口或服务状态进行检测
- path 用于等待文件或目录的创建或删除
- host 与 port 用于检测 TCP 端口就绪或关闭
- delay、sleep、timeout 分别定义首次等待、检查间隔和最长超时
文件存在检测
---
- name: wait for file creationhosts: node1tasks:- shell: sleep 10 && touch /tmp/readyasync: 20poll: 0register: async_job- name: wait until /tmp/ready appearswait_for:path: /tmp/readystate: presentdelay: 5sleep: 2timeout: 60
TCP 端口检测
---
- name: reboot and wait SSHhosts: node1,node2tasks:- name: reboot node1shell: shutdown -r now "upgrade"async: 1poll: 0when: inventory_hostname == "node1"- name: wait for node1 SSH servicewait_for:host: node1port: 22state: starteddelay: 10sleep: 5timeout: 300when: inventory_hostname == "node2"
实践建议与最佳实践
- 对易阻塞的操作优先考虑异步模式 并结合 async_status 或 wait_for 实现可靠回调
- 根据运维场景选择合适批次策略 linear、free 或使用 serial 实现滚动升级
- 在控制节点部署时 分配足够 CPU 和内存 并结合监控工具观察 forks 设置对节点负载的影响
- 定期评估 playbook 执行策略 与并发配置 确保在目标环境持续稳定运行
de2"
------## 实践建议与最佳实践- 对易阻塞的操作优先考虑异步模式 并结合 async_status 或 wait_for 实现可靠回调
- 根据运维场景选择合适批次策略 linear、free 或使用 serial 实现滚动升级
- 在控制节点部署时 分配足够 CPU 和内存 并结合监控工具观察 forks 设置对节点负载的影响
- 定期评估 playbook 执行策略 与并发配置 确保在目标环境持续稳定运行
- 在大型关键环境中 可考虑搭建 Ansible Tower 或 AWX 进一步提升并发调度与任务可视化管理能力