Как разорвать цикл в Ansible, когда какое-то условие выполнено?

Мне нужен метод, позволяющий остановить цикл в Ansible, например break в операторе for в C++ или Bash. Например, мне нужно последнее значение перед циклическим сканированием до 0.

default/main.yml

---
os_vars:
  - 8
  - 10
  - 15
  - 6
  - 0
  - 7
  - 25

tasks/main.yml

- name: Debug variables
  ansible.builtin.set_fact:
    a: "{{ item }}"
  loop: "{{ os_vars }}"
  when: item > 0

И вывод

TASK [test_role : Debug variables] *********************************************
ok: [localhost] => (item=8)
ok: [localhost] => (item=10)
ok: [localhost] => (item=15)
ok: [localhost] => (item=6)
skipping: [localhost] => (item=0)
ok: [localhost] => (item=7)
ok: [localhost] => (item=25)

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

Пожалуйста, поделитесь своими комментариями. Заранее спасибо.

Введение в Ansible Roles
Введение в Ansible Roles
Ansible - это отличный инструмент управления конфигурацией, который можно использовать для автоматизации настройки или развертывания на большом...
1
0
50
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Вопрос: «Я знаю, что могу установить другую переменную bool для управления циклом, не присваивающим следующие элементы»

Правильно, как есть

Похожие вопросы и ответы

и многое другое...

Вопрос: «Мне нужен метод, позволяющий остановить цикл в Ansible, например break в операторе for в C++ или Bash».

Такого нет. Вы не можете разорвать цикл, вы можете только реализовать пропуск.

Это потому, что

  • Что нужно знать о программировании с использованием Ansible

    Ansible не является языком: Если Ansible не является языком программирования, то что это? Ansible — это инструмент, написанный на Python, который использует декларативный язык разметки YAML для описания желаемого состояния устройств и конфигурации. ... Вы объявляете аспекты, которые хотите настроить на целевом устройстве, например, существование файла или каталога, установлен пакет, запущена служба и т. д.

  • Дзен Ansible

    Думайте декларативно: Ansible по своей сути является движком желаемого состояния. Если вы пытаетесь «написать код» в своих пьесах и ролях, вы обрекаете себя на неудачу. Наши сборники пьес на основе YAML никогда не предназначались для программирования.

Вопрос: «Мне также нужно сэкономить время, чтобы повысить производительность этой книги, поскольку иногда тело цикла может представлять собой огромный массив, и нам не нужно проверять следующие элементы, когда какое-то условие соответствует».

Если вам нравится или вам необходимо реализовать такое поведение, возможно, вам придется написать что-нибудь самостоятельно. Смотрите на примере Стоит ли разрабатывать модуль? и Разработка модулей.

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

os_vars:
  - 8
  - 10
  - 15
  - 6

чтобы обеспечить цикл. Тогда вообще не потребуется никакого разрыва или конструкции if then else.

Дальнейшее чтение


Основываясь на приведенных комментариях и, насколько я понял, вариант использования, возможный подход к решению без BREAK, when: или какой-либо конструкции IF, THEN, ELSE.

Минимальный пример сборника сценариев

---
- hosts: localhost
  become: false
  gather_facts: false

  vars:

    os_vars:
      - 8
      - 10
      - 15
      - 6
      - 0
      - 7
      - 25

  tasks:

  - name: Loop up to idx
    debug:
      msg: "{{ item }}"
    loop: "{{ os_vars[:idx | int] }}"
    loop_control:
      extended: true
      label: "{{ ansible_loop.index }}"
    # Get index of zero (0) value
    vars:
      idx: "{{ os_vars.index(os_vars | min) }}"

приведет к выводу

TASK [Loop up to idx] ********
ok: [localhost] => (item=1) =>
  msg: 8
ok: [localhost] => (item=2) =>
  msg: 10
ok: [localhost] => (item=3) =>
  msg: 15
ok: [localhost] => (item=4) =>
  msg: 6

На основе

Большое спасибо за ваш подробный ответ. Теперь мы видим — кто-то хотел добавить эту функцию из 2019 года, но она до сих пор недоступна... :(

EisenWang 09.08.2024 10:58

Верно. Но я хотел бы еще раз порекомендовать вам тщательно продумать вариант использования. Возможно, вы сможете Удалить пункты из списка раньше. Чтобы помочь в этом, нам понадобится еще один вопрос с более подробным описанием вашей структуры данных и того, чего вы пытаетесь достичь, вместо того, чтобы сосредоточиться на возможном решении.

U880D 09.08.2024 11:02

Кроме того, должна быть возможность реализовать пользовательский фильтр на основе Как удалить элемент из списка по индексу или просто использовать Нотацию фрагментов Python для доступа к элементам списка. Найдите индекс 0 и выполните цикл только по списку до этого индекса.

U880D 09.08.2024 11:09

Еще раз спасибо... Ваш комментарий очень поучителен... Посмотрю, подумаю... :)

EisenWang 09.08.2024 11:15

Пожалуйста, найдите возможный подход к решению на основе приложенных комментариев.

U880D 09.08.2024 11:44

Большое спасибо. Используя ваш пример кода, я переписываю свою книгу пьес с ограниченным массивом, например -- with_items: "{{ checkfile_lines[(table_head_index|int):(table_close_index|in‌​t)] }}".. И это работает нормально. Время работы сократилось с 5м до 20с....еще раз спасибо.

EisenWang 12.08.2024 13:51

Другие вопросы по теме