高级剧本语法

此页面上的高级 YAML 语法示例提供更多对 Ansible 使用的 YAML 文件中放置的数据的控制。你可以在官方 PyYAML 文档 中找到有关 Python 特定 YAML 的更多信息。

不安全或原始字符串

在处理由查找插件返回的值时,Ansible 使用一种名为 unsafe 的数据类型来阻止模板化。将数据标记为不安全可以防止恶意用户滥用 Jinja2 模板在目标机器上执行任意代码。Ansible 实现确保永远不会对不安全值进行模板化。它比使用 {% raw %} ... {% endraw %} 标签转义 Jinja2 更全面。

你可以在你定义的变量中使用相同的 unsafe 数据类型,以防止模板化错误和信息泄露。你可以将由 vars_prompts 提供的值标记为不安全。你也可以在剧本中使用 unsafe。最常见的用例包括允许特殊字符(如 {%)的密码,以及看起来像模板但不应该进行模板化的 JSON 参数。例如

---
mypassword: !unsafe 234%234{435lkj{{lkjsdf

在剧本中

---
hosts: all
vars:
  my_unsafe_variable: !unsafe 'unsafe % value'
tasks:
    ...

对于哈希或数组等复杂变量,在各个元素上使用 !unsafe

---
my_unsafe_array:
  - !unsafe 'unsafe element'
  - 'safe element'

my_unsafe_hash:
  unsafe_key: !unsafe 'unsafe value'

YAML 锚点和别名:共享变量值

YAML 锚点和别名 帮助你定义、维护和灵活使用共享变量值。你使用 & 定义一个锚点,然后使用别名引用它,用 * 表示。以下是一个示例,使用锚点设置三个值,使用别名使用其中两个值,并覆盖第三个值

---
...
vars:
  app1:
    jvm: &jvm_opts
      opts: '-Xms1G -Xmx2G'
      port: 1000
      path: /usr/lib/app1
  app2:
    jvm:
      <<: *jvm_opts
      path: /usr/lib/app2
...

这里,app1app2 使用锚点 &jvm_opts 和别名 *jvm_opts 共享 optsport 的值。 path 的值通过 <<合并运算符 合并。

锚点和别名还允许你共享复杂的变量值集,包括嵌套变量。如果你有一个包含另一个变量值的变量值,你可以分别定义它们

vars:
  webapp_version: 1.0
  webapp_custom_name: ToDo_App-1.0

这是低效的,而且在大规模情况下意味着更多的维护。为了将版本值合并到名称中,你可以在 app_version 中使用锚点,在 custom_name 中使用别名

vars:
  webapp:
      version: &my_version 1.0
      custom_name:
          - "ToDo_App"
          - *my_version

现在,你可以在 custom_name 的值中重用 app_version 的值,并在模板中使用输出

---
- name: Using values nested inside dictionary
  hosts: localhost
  vars:
    webapp:
      version: &my_version 1.0
      custom_name:
        - "ToDo_App"
        - *my_version
  tasks:
  - name: Using Anchor value
    ansible.builtin.debug:
      msg: My app is called "{{ webapp.custom_name | join('-') }}".

你使用 &my_version 锚点锚定了 version 的值,并使用 *my_version 别名重新使用了它。锚点和别名允许你访问字典内的嵌套值。

另请参阅

使用变量

关于变量的一切

操作数据

在 Ansible 中进行复杂的数据操作

沟通

有疑问?需要帮助?想分享你的想法?访问 Ansible 沟通指南