Ansible: накопление выходных данных нескольких процессов

#ansible

#ansible

Вопрос:

У меня есть следующий сценарий:

 ---
- hosts: localhost
  gather_facts: false
  vars:
    db_process:
      - mysqld
      - db2sys
      - oracle*
      - pmon
  tasks:
    - shell: ps -ef | grep '{{ item }}' | grep -v grep | wc -l ; pgrep -x '{{ item }}' | wc -l
      loop: "{{ db_process }}"
      changed_when: false
      register: ps_out
    - debug:
        msg: "{{ item }}"
      loop: "{{ ps_out.results }}"
    - name: combine output
      set_fact:
        db_process_status: '{% if item.stdout_lines[0]|int == 0 and item.stdout_lines[1]|int == 0 %}pass{% else %}fail{% endif %}'
        db_process_message: '{{ item.item }} {% if item.stdout_lines[0]|int == 0 and item.stdout_lines[1]|int == 0 %}Not Found{% else %}Found{% endif %}'
      loop: "{{ ps_out.results }}"

 

После выполнения этой задачи я должен объединить все результаты db_process_message в надлежащий формат JSON.

Есть ли какой-нибудь способ вместо группировки накапливать выходные данные по нескольким процессам и регистрировать их в переменной?

Ожидаемый результат:

 [
    "mysqld Not Found",
    "db2sys Not Found",
    "oracle Not Found",
    "pmon Not Found"
]
 

Комментарии:

1. Почему вы бы использовали ps для этого? Есть факты, которые вы можете собрать, связанные со службами: docs.ansible.com/ansible/latest/collections/ansible/builtin /…

Ответ №1:

В вашей set_fact задаче вы перезаписываете на каждой итерации по переменной цикла значения db_process_status и db_process_message . Вместо этого вам нужно заполнить два списка, по одному для каждой переменной, чтобы сохранять их значения при каждом запуске цикла.

вот задача, которая может это сделать, ваш код был перемещен в строки var1 и var2 , и новый код добавляет эти значения в два списка:

задача:

   - name: combine output
    set_fact:
      db_process_status: '{{ db_process_status|default([])   [var1] }}'
      db_process_message: '{{ db_process_message|default([])   [var2] }}'
    vars:
      var1: '{% if item.stdout_lines[0]|int == 0 and item.stdout_lines[1]|int == 0 %}pass{% else %}fail{% endif %}'
      var2: '{{ item.item }} {% if item.stdout_lines[0]|int == 0 and item.stdout_lines[1]|int == 0 %}Not Found{% else %}Found{% endif %}'
    loop: "{{ ps_out.results }}"

  - name: print db_process_status
    debug:
      var: db_process_status

  - name: print db_process_message
    debug:
      var: db_process_message
 

пример вывода (я добавил sshd, чтобы продемонстрировать, что он распознает его как запущенный):

 TASK [print db_process_status] ****************************************************************************************************************************************************************************************
ok: [localhost] => {
    "db_process_status": [
        "pass",
        "pass",
        "pass",
        "pass",
        "fail"
    ]
}

TASK [print db_process_message] ***************************************************************************************************************************************************************************************
ok: [localhost] => {
    "db_process_message": [
        "mysqld Not Found",
        "db2sys Not Found",
        "oracle* Not Found",
        "pmon Not Found",
        "sshd Found"
    ]
}