Можно ли установить факт, содержащий массив в недоступном, используя set_fact
? Какой правильный синтаксис для него?
Можно ли установить факт массива в Ansible?
Ответ 1
В самом деле. Вам нужно процитировать весь массив:
- name: set fact
set_fact: foo="[ 'one', 'two', 'three']"
- name: debug
debug: msg={{ item }}
with_items: foo
Вышеупомянутые задачи должны генерировать следующий вывод:
TASK: [set fact] **************************************************************
ok: [localhost]
TASK: [debug] *****************************************************************
ok: [localhost] => (item=one) => {
"item": "one",
"msg": "one"
}
ok: [localhost] => (item=two) => {
"item": "two",
"msg": "two"
}
ok: [localhost] => (item=three) => {
"item": "three",
"msg": "three"
}
Ответ 2
Да, это возможно. Как упоминалось в другом ответе, вы можете установить массив, используя двойные кавычки, например:
- name: set foo fact to an array
set_fact: foo="[ 'one', 'two', 'three' ]"
Однако, я думал, что создаю еще один ответ, чтобы указать, что его также можно добавить в существующий массив, например:
- name: add items to foo array fact
set_fact: foo="{{foo}} + [ 'four' ]"
Объединив их и добавив отладку в качестве playbook (который я называю facts.yml
) следующим образом:
---
- name: test playbook
gather_facts: false
hosts: localhost
tasks:
- name: set foo fact to an array
set_fact: foo="[ 'one', 'two', 'three' ]"
- debug: var=foo
- name: add items to foo array fact
set_fact: foo="{{foo}} + [ 'four' ]"
- debug: var=foo
Производит (через ansible-playbook facts.yml
) следующее:
PLAY [test playbook] **********************************************************
TASK: [set foo fact to an array] **********************************************
ok: [localhost]
TASK: [debug var=foo] *********************************************************
ok: [localhost] => {
"foo": [
"one",
"two",
"three"
]
}
TASK: [add items to foo array fact] *******************************************
ok: [localhost]
TASK: [debug var=foo] *********************************************************
ok: [localhost] => {
"foo": [
"one",
"two",
"three",
"four"
]
}
PLAY RECAP ********************************************************************
localhost : ok=4 changed=0 unreachable=0 failed=0
Ответ 3
Добавляя к уже предоставленным ответам, я хотел бы показать вам другой способ
определите список с помощью set_fact
, используя обычный синтаксис YAML вместо
который Ansible core предпочитает использовать в своих документах. Эта
пользовательский формат, как в этом случае, показал, что это приводит к путанице.
Рассмотрим следующий пример:
- name: 'Set the foo variable to a static list using the YAML syntax'
set_fact:
foo:
- 'one'
- 'two'
- 'three'
Прямо вперед, не так ли? Как и в любом нормальном документе YAML. Так почему бы и не использовать его в файле задач Ansible YAML?
О комбинации списков, упомянутых @lindes-hw. Существует более одного способ сделать это. В следующих примерах для определения списка используется синтаксис Jinja2:
- name: 'Set the foo variable to a combined static list using the Jinja2 syntax'
set_fact:
foo: '{{ [ "one" ] + [ "two", "three" ] }}'
- name: 'Set the foo variable to a combined static list using the Jinja2 syntax and Jinja2 filters'
set_fact:
foo: '{{ [ "one" ] | union([ "two", "three" ]) }}'
Во втором примере используется фильтр union
. См. набор фильтров теории в документах Ansible.
Ответ 4
У меня было аналогичное требование для создания списка объектов сервера на основе списка IP-адресов.
vars:
server_ips: one,two,three
tasks:
- name: build items list
set_fact:
foo: "{{foo|default([]) + [{'ip': {'addr': item, 'type': 'V4'}}] }}"
with_items: "{{server_ips.split(',')}}"
- debug:
msg: "{{ foo }}"
Дает следующий результат
TASK [setup] *******************************************************************
ok: [localhost]
TASK [build items list] ********************************************************
ok: [localhost] => (item=one)
ok: [localhost] => (item=two)
ok: [localhost] => (item=three)
TASK [debug] *******************************************************************
ok: [localhost] => {
"msg": [
{
"ip": {
"addr": "one",
"type": "V4"
}
},
{
"ip": {
"addr": "two",
"type": "V4"
}
},
{
"ip": {
"addr": "three",
"type": "V4"
}
}
]
}