如何使用Ansible获取已安装的YUM软件包?

6
我正在尝试获取安装在RHEL机器上的所有已安装YUM软件包。我可以通过使用shell命令轻松获取它,但这不是幂等的,并且我想改用YUM命令。这个shell命令运行良好:
- name: yum list packages
  shell: yum list installed > build_server_info.config

但是当我尝试使用YUM命令时,它只是执行了,但是没有给出任何结果。
- name: yum_command
  action: yum list=${pkg} list=available
4个回答

19

使用shell命令可以轻松获取,但这不是幂等的。

当你正在查询机器的当前状态时,你不能真正谈论幂等性。

“幂等”意味着无论你运行某个任务多少次,该任务都会确保机器处于所需状态。

当你查询当前状态时,你并没有描述所需状态。无论你做什么,使用什么方法,“幂等”这个术语都不适用。

关于你的例子,这个任务应该失败,因为你重复了相同的参数“list”,但它并没有失败,看起来像是Ansible的一个怪异问题。

要获取已安装软件包的列表,请使用:


- name: yum_command 
  yum:
    list=installed
  register: yum_packages

- debug:
    var: yum_packages

它将每个软件包的描述存在一个变量 yum_packages 中作为字典列表。
您可以使用 JSON 查询过滤器 来获取单个软件包 (tar):
- debug: var=item
  with_items: "{{yum_packages|json_query(jsonquery)}}"
  vars:
    jsonquery: "results[?name=='tar']"

要获得这样的结果:

"item": {
    "arch": "x86_64",
    "epoch": "2",
    "name": "tar",
    "nevra": "2:tar-1.26-31.el7.x86_64",
    "release": "31.el7",
    "repo": "installed",
    "version": "1.26",
    "yumstate": "installed"
}

或仅其版本:

- debug: var=item
  with_items: "{{yum_packages|json_query(jsonquery)}}"
  vars:
    jsonquery: "results[?name=='tar'].version"

"item": "1.26"

如果你只需要一个可在其他地方使用的软件包列表,那么你要找的jsonquery{{ yum_packages | json_query('results[*].name') }}。结合| difference()非常有用,例如可以获取缺失软件包的列表。 - DustWolf

8
自 Ansible 2.5 版本以来,您还可以使用 package_facts 模块:它将收集安装包列表作为 Ansible 事实。以下是从 CPU 的示例:
- name: get the rpm package facts
  package_facts:
    manager: rpm

- name: show them
  debug: var=ansible_facts.packages

0

嗯,yum模块的官方Ansible文档将list描述为:

"用于与 /usr/bin/ansible 一起使用而不是playbook的各种(非幂等)命令。"

所以如果你想要找到一个幂等的 list 调用,你就会没有运气。

如果你只是想禁止 changed 输出,请changed_when参数设置为False

(另外,拥有重复的 list 参数是可疑的。)


这将再次使用 shell 模块的相同方法。 - user_dev
好的。采用techraf的解决方案,它包含了我完全忽略的额外的“register”操作。 - Kyle
两个链接都(实际上)已经失效了:“糟糕!您查看的 Ansible 文档版本不包含该页面。” - Peter Mortensen

0
如果您的需求是仅检查一个软件包,并基于此执行另一个任务,则可以使用package_facts模块。
- name: install docker community edition in rhel8
  hosts: localhost
  connection: local

  tasks:
   - name: Gather the rpm package facts
     package_facts:
       manager: auto

   - name: check if docker-ce is already installed
     debug:
       var: ansible_facts.packages['docker-ce']


   - name: using command module to install docker-ce
     command: yum install docker-ce --nobest -y
     when: "'docker-ce' not in ansible_facts.packages"
     register: install_res

   - name: whether docker is installed now
     debug:
       var: install_res

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接