Ansible 2.8 Roles - использование каталога vars/main

Я пытаюсь разбить свои переменные роли Ansible на несколько файлов - согласно этому ответу должно быть возможно создатьvars/main каталог, и все файлы.yml в этом каталоге должны быть загружены автоматически.

Однако в моем случае этого не происходит.

Моя структура каталогов:

vars
└── main
    ├── gce_settings.yml
    ├── vsphere_settings.yml
    └── vsphere_zone.yml

Однако, когда я пытаюсь использовать переменную, определенную внутри vsphere_settings.yml, Ansible жалуется, что переменная не определена:{"msg": "The task includes an option with an undefined variable. The error was: 'vsphere_user' is undefined

Если я перенесу объявление переменной в vars/main.yml, все работает как положено. Но, конечно, я бы предпочел разделить свои переменные на несколько файлов.

Мне не удалось найти упоминания об этой "возможности" в официальной документации Ansible, и я не знаю, как я могу ее устранить. Может кто-то указать мне верное направление?

Моя доступная версия:ansible 2.8.5 в Ubuntu 16.04

И прежде чем вы спросите: да, я убедился, что main.yml не присутствовал при попытке загрузить vars/main/*.yml...

2 ответа

Решение

Версия TL;DR: это ошибка недоступности, вызванная наличием пустых файлов.yml в vars/main. Для этого уже есть пиар. Смотрите здесь.

Фактический результат (как упоминалось в комментариях) на самом деле зависит от порядка обработки файлов (по умолчанию похоже, что мой Ansible обрабатывает их в алфавитном порядке, но это может зависеть от версии или базовой ОС):

  • Если сначала обрабатывается пустой файл, вы получаете сообщение об ошибке: ERROR! failed to combine variables, expected dicts but got a 'NoneType' and a 'AnsibleMapping'
  • Если пустой файл обрабатывается после других файлов, сообщение об ошибке отсутствует, но все переменные, которые были установлены до этого момента, уничтожаются.

Подробнее: поскольку я понятия не имею, как устранить это в самом Ansible, я перешел к коду и начал добавлять print заявления, чтобы увидеть, что происходит.

В моем случае у меня было несколько пустых файлов.yml в папке vars/main каталог (файлы, которые я планировал заполнить позже. Ну... похоже, когда код встречает такой пустой файл, он уничтожает весь словарь, который он создал до сих пор.

Либо я упускаю что-то очень важное, либо это ошибка... Шаги по воспроизведению:

  • создать роль
  • создать vars/main каталог и заполните его некоторыми файлами.yml
  • добавить пустой файл.yml (названный так, чтобы он обрабатывался после других файлов)
  • попробуйте распечатать переменные из первых файлов
    ansible# tree roles 
    roles
    +-- test
        +-- tasks
        ¦   +-- main.yml
        +-- vars
            +-- main
                +-- correct_vars.yml

    4 directories, 2 files

    ansible# cat roles/test/vars/main/correct_vars.yml  myname: bogd

    ansible# ansible-playbook -i inventory.yml test.yml 
    ... 
    ok: [localhost] => {
        "myname": "bogd" } 
    ...

    ansible# echo > roles/test/vars/main/emptyfile.yml

    ansible# ansible-playbook -i inventory.yml test.yml 
    ... ok: [localhost] => {
        "myname": "VARIABLE IS NOT DEFINED!" } 
    ...

Позже отредактируйте: да, это ошибка... Смотрите здесь.

Пример ниже

$ cat play.yml 
- hosts: localhost
  roles:
    - role1

$ cat roles/role1/tasks/main.yml 
- debug:
    var: var1

$ cat roles/role1/vars/main/var1.yml 
var1: test_var1

дает

"var1": "test_var1"
Другие вопросы по тегам