Dictionary 结果中嵌套项的Ansible循环

Dictionary 结果中嵌套项的Ansible循环,dictionary,ansible,Dictionary,Ansible,使用ansible I部署ubuntu 18.04服务器时遇到以下问题: 我想安装的一些软件包既不在官方回购协议中,也不在PPA中。所以我必须从github下载并安装它们 我检查是否已使用dpkg query-W安装了软件包,并且仅当返回代码为1时才运行以下安装任务。像这样: # ripgrep - name: "Check if ripgrep is installed" command: dpkg-query -W ripgrep register: ripgrep_dpkg_che

使用ansible I部署ubuntu 18.04服务器时遇到以下问题:

我想安装的一些软件包既不在官方回购协议中,也不在PPA中。所以我必须从github下载并安装它们

我检查是否已使用
dpkg query-W
安装了软件包,并且仅当返回代码为
1
时才运行以下安装任务。像这样:

# ripgrep
- name: "Check if ripgrep is installed"
  command: dpkg-query -W ripgrep
  register: ripgrep_dpkg_check
  failed_when: ripgrep_dpkg_check.rc > 1
  changed_when: ripgrep_dpkg_check.rc == 1

- name: "Install ripgrep from github
  apt:
     deb: "https://github.com/BurntSushi/ripgrep/releases/download/11.0.2/ripgrep_11.0.2.deb"
  when: ripgrep_dpkg_check.rc == 1
对于单个包来说,这是很好的,但是对于多个包来说,它会变得单调乏味

因此,我考虑在包含我的包信息的散列上循环,如下所示:

extrapackages:
 - { name: ripgrep , version: 2.0, url: awfawf }
 - { name: fd, version: 1.4, url: awfdawf }
然后在它上面循环:

- name: "Check if package is installed"
  command: "dpkg-query -W {{ item.name }}"
  register: dpkg_check
  loop: "{{ extrapackages }}"
这给了我:

"dpkg_check": {
    "changed": true,
        "msg": "All items completed",
        "results": [
        {
            "ansible_loop_var": "item",
            "changed": true,
            "cmd": [
                "dpkg-query",
            "-W",
            "ripgrep"
            ],
            "delta": "0:00:00.015585",
            "end": "2019-11-27 17:18:42.951019",
            "failed": false,
            "invocation": {
                "module_args": {
                    "_raw_params": "dpkg-query -W ripgrep",
                    "_uses_shell": false,
                    "argv": null,
                    "chdir": null,
                    "creates": null,
                    "executable": null,
                    "removes": null,
                    "stdin": null,
                    "stdin_add_newline": true,
                    "strip_empty_ends": true,
                    "warn": true
                }
            },
            "item": {
                "name": "ripgrep",
                "url": "awfawf",
                "version": 2.0
            },
            "rc": 0,
            "start": "2019-11-27 17:18:42.935434",
            "stderr": "",
            "stderr_lines": [],
            "stdout": "ripgrep\t11.0.2",
            "stdout_lines": [
                "ripgrep\t11.0.2"
            ]
        },
        {
            "ansible_loop_var": "item",
            "changed": true,
            "cmd": [
                "dpkg-query",
            "-W",
            "fd"
            ],
            "delta": "0:00:00.015857",
            "end": "2019-11-27 17:18:43.137177",
            "failed": false,
            "invocation": {
                "module_args": {
                    "_raw_params": "dpkg-query -W fd",
                    "_uses_shell": false,
                    "argv": null,
                    "chdir": null,
                    "creates": null,
                    "executable": null,
                    "removes": null,
                    "stdin": null,
                    "stdin_add_newline": true,
                    "strip_empty_ends": true,
                    "warn": true
                }
            },
            "item": {
                "name": "fd",
                "url": "awfdawf",
                "version": 1.4
            },
            "rc": 0,
            "start": "2019-11-27 17:18:43.121320",
            "stderr": "",
            "stderr_lines": [],
            "stdout": "fd\t7.4.0",
            "stdout_lines": [
                "fd\t7.4.0"
            ]
        }
    ]
}
现在我想为所有循环项运行apt,这些循环项具有
rc=1
。在伪代码中,我需要如下内容:

for package in dpkg_check.results:
    if package.rc = 1:
        apt install package.item.url

这样的事情在ansible中可能发生吗

使用json\u查询。比如说

- apt:
    name: "{{ dpkg_check.results|
              json_query('[?rc == `1`].item.url') }}"
- debug:
    msg: "{{ dpkg_check.results|
             json_query('[?rc == `1`].item.url') }}"
首先用debug测试它。比如说

- apt:
    name: "{{ dpkg_check.results|
              json_query('[?rc == `1`].item.url') }}"
- debug:
    msg: "{{ dpkg_check.results|
             json_query('[?rc == `1`].item.url') }}"

(未测试)

非常感谢@Vladimir Botka,这正是我想要的

我的工作解决方案:

- name: "Check if extra packages are installed"                                                                                                                                                                               
  command: "dpkg-query -W {{ item.name }}"                                                                                                                                                                                    
  register: dpkg_check                                                                                                                                                                                                        
  loop: "{{ extrapackages }}"                                                                                                                                                                                                 
  failed_when: dpkg_check.rc > 1                                                                                                                                                                                              
  changed_when: dpkg_check.rc == 1                                                                                                                                                                                            

- name: "Install missing extra packages"                                                                                                                                                                                      
  apt:                                                                                                                                                                                                                        
  deb: "{{ item }}"                                                                                                                                                                                                         
  loop: "{{ dpkg_check.results|json_query('[?rc == `1`].item.url') }}"                                                                                                                                                        
  when: dpkg_check.changed