Ansible:将命令参数作为列表传递

Ansible:将命令参数作为列表传递,ansible,Ansible,我想在一个变量中以列表的形式存储多个参数 vars: my_args: - --verbose - --quiet - --verify 然后将列表作为带引号的参数传递给命令。最明显的join 过滤器没有像我预期的那样工作。它生成一个包含所有列表元素的单词,而不是每个列表元素一个单词: tasks: - command: printf '%s\n' "{{ my_args | join(' ') }}" ... changed: [localhost] =>

我想在一个变量中以列表的形式存储多个参数

vars:
  my_args:
    - --verbose
    - --quiet
    - --verify
然后将列表作为带引号的参数传递给命令。最明显的
join
过滤器没有像我预期的那样工作。它生成一个包含所有列表元素的单词,而不是每个列表元素一个单词:

tasks:
  - command: printf '%s\n' "{{ my_args | join(' ') }}"
...
changed: [localhost] => {
"changed": true,
"cmd": [
    "printf",
    "%s\\n",
    " --quiet  --verbose  --verify "
],

STDOUT:

 --quiet  --verbose  --verify

如何将它们传递给命令?

要将列表元素作为参数传递给模块,请使用
map('quote')| join(“”)
过滤器或
for
循环:

tasks:

- name: Pass a list as arguments to a command using filters
  command: executable {{ my_args | map('quote') | join(' ') }}

- name: Pass a list as arguments to a command using for loop
  command: executable {% for arg in my_args %} "{{ arg }}" {% endfor %}
不要在过滤器中使用引号,但要在循环中使用引号。虽然
for
循环稍微长一些,但它提供了更多塑造输出的可能性。例如,为列表项添加前缀或后缀,如
“prefix{{item}}suffix”
,或对该项应用筛选器,甚至使用
循环有选择地处理项。*

这方面的例子是:

tasks:
  - command: printf '%s\n' {{ my_args | map('quote') | join(' ') }}
  - command: printf '%s\n' {% for arg in my_args %} "{{ arg }}" {% endfor %}
...
changed: [localhost] => {
    "changed": true,
    "cmd": [
        "printf",
        "%s\\n",
        "--quiet",
        "--verbose",
        "--verify"
    ],

STDOUT:

--quiet
--verbose
--verify
列表元素不仅限于简单字符串,还可以包含一些逻辑:

vars:
  my_args:
    - --dir={{ my_dir }}
    - {% if my_option is defined %} --option={{ my_option }} {% endif %}

{{my_args | join('')}}
怎么样?如果出于任何原因需要引用参数,那么
“{{my_args | join}}”将生成一个单词,即一个参数。带有
“{{arg}}”
的for循环将生成单独的单词。您可以应用筛选器<代码>{mylist | map('quote')| join(''')}
这并不像您所期望的那样工作。尝试
-command:printf“%s\n”{{{my_args|map('quote')|join(''''}}}}
,并与
-command:printf“%s\n'{my_args%}{{arg arg}{%endfor%}
进行比较。现在,关于双引号的评论很有用。我会把它包括在答案中。