如何过滤Ansible JSON输出以提取Linux补丁安装详情?
Ansible提取Linux补丁安装中Installed条目问题解决
问题背景
通过Ansible自动化执行Linux补丁安装时,需要从执行后的输出中仅提取标注为“Installed”的补丁详情,但编写的测试Playbook(读取本地JSON文件)及实际补丁Playbook均无法正常输出目标内容,运行时报错。
错误Playbook分析与修正
测试Playbook(读取本地JSON文件)
原Playbook存在语法错误、变量结构误解及查询路径错误:
- debug任务的
msg参数未使用正确的键值对语法(应使用:而非=); - 对register后的变量结构理解错误,且目标数据是字符串数组而非字典,无法直接用
json_query查询Installed字段。
修正后的测试Playbook:
--- - hosts: localhost gather_facts: no vars: contents: "{{ lookup('file', '/ansible/linuxpatch.json') | from_json }}" tasks: - name: 筛选所有Installed开头的补丁条目 set_fact: result: "{{ contents.msg[2] | select('match', '^Installed:') | list }}" - name: 输出提取结果 debug: var: result
提取逻辑Playbook
原Playbook的json_query查询逻辑错误,因为目标数据是字符串数组,而非包含Installed字段的字典集合。
修正后的提取逻辑:
- name: 提取Installed补丁信息 set_fact: update_info: "{{ msg.msg[2] | select('match', '^Installed:') | list }}"
实际补丁安装Playbook
原Playbook存在变量处理错误、重启后变量丢失、变量名不匹配等问题:
- 错误处理yum模块返回的结果,无需用
list.values() | list; - 重启后register的变量会失效,导致后续无法获取补丁信息;
- 最终debug的变量名与set_fact的变量名不匹配。
修正后的实际补丁Playbook:
- hosts: prod become: yes tasks: - name: 清理yum缓存 shell: yum clean all - name: 安装所有系统更新补丁 yum: name: '*' state: latest register: yum_update_result - name: 提取Installed补丁详情 set_fact: installed_patches: "{{ yum_update_result.results | select('search', '^Installed:') | list }}" when: yum_update_result.changed - name: 保存补丁信息到本地(避免重启后丢失) copy: content: "{{ installed_patches | to_nice_json }}" dest: "/tmp/installed_patches_{{ inventory_hostname }}.json" when: yum_update_result.changed - name: 重启服务器(仅当有补丁安装时) reboot: reboot_timeout: 3600 when: yum_update_result.changed - name: 读取保存的补丁信息(重启后恢复) set_fact: installed_patches: "{{ lookup('file', '/tmp/installed_patches_{{ inventory_hostname }}.json') | from_json }}" when: yum_update_result.changed - name: 输出Installed补丁详情 debug: var: installed_patches when: yum_update_result.changed
关键要点说明
- yum模块结果处理:yum模块执行后,
yum_update_result.results字段直接包含所有安装/移除的补丁信息字符串数组,无需额外转换; - 筛选逻辑:使用
select('match', '^Installed:')直接筛选以Installed:开头的字符串,比json_query更适配当前数据结构; - 重启后变量保留:由于Ansible重启后会丢失之前的register变量,需在重启前将补丁信息写入本地文件,重启后再读取;
- 条件执行:通过
when: yum_update_result.changed确保仅在有补丁安装时执行后续操作,避免无意义的步骤。
内容的提问来源于stack exchange,提问作者Rakesh
相关产品推荐
相关产品推荐

