Могу ли я создавать динамические списки в Ansible vars_files? - PullRequest
0 голосов
/ 31 октября 2019

У меня есть файл переменных, который содержит важную информацию о наших базах данных;сервер, на котором они находятся, версия базы данных, каталог DB_HOME и т. д. В файле переменных я хотел бы динамически создавать списки, которые собирают уникальные значения этих свойств, чтобы их можно было легко выполнить в задаче.

Я обладаю эквивалентной функциональностью, создавая список "на лету" в параметре задачи loop , но это означает повторение этого синтаксиса цикла (нарушает принцип DRY), и я хотел бы, чтобы менее опытные коллеги Ansible имели возможностьиспользовать предопределенный список.

пример файла переменных database.yml:

databases:
- name: test_db1
  server: ora_901
  listener: LISTENER_XYZ
  version: '11.2.0.4'
  oracle_home: '/app/oracle/product/11.2.0.4/db_home'

- name: test_db2
  server: ora_902
  listener: LISTENER_ABC
  version: '11.2.0.4'
  oracle_home: '/app/oracle/product/11.2.0.4/db_home'

## This didn't work... was hoping I could build this list dynamically
listeners:
- name: "{{ item }}"
  loop:  "{{ databases | map(attribute = 'listener') | list | unique }}"

servers:
- name: "{{ item }}"
  loop:  "{{ databases | map(attribute = 'server') | list | unique }}"

Затем я бы использовал этот цикл непосредственно для списков «слушателей» или «серверов». с некоторыми задачами.

Когда я попытался выполнить задачу, ссылающуюся на переменную listeners, она не удалась. Работа с базами данных работает, и все элементы возвращаются, поэтому я знаю, что он получает некоторые данные из файла vars_file ...

- vars_files:
    - vars/databases.yml
  tasks:
  - debug: 
      msg: "{{ databases }}"
  - debug:
      msg: "{{ listeners }}"

TASK [debug] **************************************************************************
ok: [FQDN] => {
    "msg": [
        {
            "listener": "LISTENER_XYZ",
            "name": "test_db1",
            "oracle_home": "/app/oracle/product/11.2.0.4/db_home",
            "server": "ora_901",
            "version": "11.2.0.4"
        },
        {
            "listener": "LISTENER_ABC",
            "name": "test_db2",
            "oracle_home": "/app/oracle/product/11.2.0.4/dbhome_1",
            "server": "ora_902",
            "version": "11.2.0.4"
        },

fatal: [FQDN]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'item' is undefined\n\nThe error appears to have been in '/home/xxx/test_vars.yml': line 21, column 5, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n\n  - debug:\n    ^ here\n"}

Мне бы очень хотелось сохранить эти динамические определения в том же месте, что и определения сервера, ине понимаю, почему это невозможно, я просто уверен, что использую неправильный механизм.

1 Ответ

0 голосов
/ 03 ноября 2019

Проверьте это из Ansible doc // Просто, чтобы дать вам представление о " loop_control ".

Вы можете вложить две циклические задачи, используя include_tasks. Однако по умолчанию Ansible устанавливает элемент переменной цикла для каждого цикла. Это означает, что внутренний вложенный цикл перезапишет значение элемента из внешнего цикла. Вы можете указать имя переменной для каждого цикла, используя loop_var с loop_control:

# main.yml
- include_tasks: inner.yml
  loop:
    - 1
    - 2
    - 3
  loop_control:
    loop_var: outer_item

# inner.yml
- debug:
    msg: "outer item={{ outer_item }} inner item={{ item }}"
  loop:
    - a
    - b
    - c
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...