现在我正在使用一个Ansible中的shell脚本,如果它可以分成多行,它将更易读。
- name: iterate user groups
shell: groupmod -o -g {{ item['guid'] }} {{ item['username'] }} ....more stuff to do
with_items: "{{ users }}"
我不确定如何在Ansible shell模块中允许多行脚本
现在我正在使用一个Ansible中的shell脚本,如果它可以分成多行,它将更易读。
- name: iterate user groups
shell: groupmod -o -g {{ item['guid'] }} {{ item['username'] }} ....more stuff to do
with_items: "{{ users }}"
我不确定如何在Ansible shell模块中允许多行脚本
Ansible在playbooks中使用YAML语法。YAML具有许多块操作符:
>
是一个折叠块操作符。也就是说,它通过空格将多行合并在一起。以下语法:
key: >
This text
has multiple
lines
将值This text has multiple lines\n
分配给key
。
|
字符是一个字面块操作符。这可能是你想要的多行shell脚本。以下语法:
key: |
This text
has multiple
lines
将值This text\nhas multiple\nlines\n
分配给key
。
您可以将其用于像这样的多行shell脚本:
- name: iterate user groups
shell: |
groupmod -o -g {{ item['guid'] }} {{ item['username'] }}
do_some_stuff_here
and_some_other_stuff
with_items: "{{ users }}"
需要注意的一点是:Ansible对shell
命令的参数进行了一些奇怪的操作,因此尽管上述方法通常能按预期工作,但以下方法则不行:
- shell: |
cat <<EOF
This is a test.
EOF
实际上,Ansible会在文本前面添加空格,这意味着shell永远不会在一行的开头找到字符串EOF
。您可以通过像这样使用cmd
参数来避免Ansible的无用启发式方法:
- shell:
cmd: |
cat <<EOF
This is a test.
EOF
ansible
而不是 ansible-playbook
会怎样? - Archonshell: >
实际上会导致 Ansible 插入换行符,因此这是不正确的。 - Philipp Ludwigshell: >
的例子,而且你的说法是错误的:Ansible 不知道你是否使用 "
或 >
或 |
;它只知道在解析 YAML 后接收到的文本。>
引用操作符是一个折叠操作符,不会保留换行符。如果你看到了不同的行为,请随时提出问题,我很乐意帮忙查看。 - larsks>
下面行的缩进有一个小问题:它们必须以相同的缩进量缩进,才能正确地折叠(至少在Ansible中是这样)。我发表了一篇相关的答案。这可能就是@PhilippLudwig看到的问题? - JK Laiho尝试使用ansible 2.0.0.2:
---
- hosts: all
tasks:
- name: multiline shell command
shell: >
ls --color
/home
register: stdout
- name: debug output
debug: msg={{ stdout }}
将Shell命令折叠成单行,例如ls --color /home
参考文献(于2021年访问): https://docs.ansible.com/ansible/latest/reference_appendices/YAMLSyntax.html ==> 在页面中搜索“多行”。
在EOF分隔符前添加一个空格可以避免出现cmd的问题:
- shell: |
cat <<' EOF'
This is a test.
EOF
我更喜欢这种语法,因为它允许为shell设置配置参数:
---
- name: an example
shell:
cmd: |
docker build -t current_dir .
echo "Hello World"
date
chdir: /home/vagrant/
>
的一个小提示,曾经让我困惑了一段时间:在使用Ansible时,缩进在它下面的行必须处于相同的缩进级别才能正确地进行折叠。\
行结尾,并将第一行以下的每一行缩进了两个空格。我使用了shell: >
,删除了反斜杠并保留了现有的缩进。>
应该将它们转换为空格。# Converts into ls -la /tmp, as expected
- name: working shell command that folds newlines
shell: >
ls
-la
/tmp
# Tries to run -la and /tmp as their own commands
- name: failing shell command that does not fold newlines
shell: >
ls
-la
/tmp
- name: Add a line to a file if the file does not exist
ansible.builtin.lineinfile:
path: ~/.ssh/config
line: |
Host {{item.COMPONENT}} {{item.COMPONENT}}.{{ZONE}}
HostName {{r53_var_one.resource_record_sets[0].resource_records[0].value}}
User centos
Port 22
IdentityFile ~/.ssh/key.pem
StrictHostKeyChecking no
create: yes
mode: '0600'
- hosts: all,localhost
tasks:
- name: greather_than
debug:
msg: >
a
b
c
- name: pipe
debug:
msg: |
a
b
c
# ansible-playbook test.yml
[WARNING]: provided hosts list is empty, only localhost is available. Note that the implicit localhost does not match 'all'
PLAY [all,localhost] ***************************************************************************
TASK [Gathering Facts] *************************************************************************
ok: [localhost]
TASK [greater_than] ****************************************************************************
ok: [localhost] => {
"msg": "a b c\n"
}
TASK [pipe] ***********************************************************************************
ok: [localhost] => {
"msg": "a \nb\nc\n"
}
PLAY RECAP ***********************************************************************************
localhost : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
#