Durante l'esecuzione di attività in playbook Ansible , potresti imbatterti in alcune attività di natura ripetitiva. Queste sono attività che richiedono la creazione di più riproduzioni, cosa che può essere piuttosto noiosa. Come con qualsiasi linguaggio di programmazione, i loop in Ansible forniscono un modo più semplice per eseguire attività ripetitive utilizzando meno righe di codice in un playbook.
Durante la creazione di loop, Ansible fornisce queste due direttive:loop e con_* parola chiave.
La parola chiave loop è stata aggiunta di recente ad Ansible 2.5 . La parola chiave loop viene solitamente utilizzata per creare loop semplici e standard che ripetono diversi elementi.
Il con_* la parola chiave viene utilizzata con numerosi plug-in di ricerca durante l'iterazione dei valori. I plug-in di ricerca consentono ad Ansible di accedere alle informazioni da fonti esterne come archivi dati esterni, filesystem ecc. Il with_* la ricerca è ancora molto in uso e non è ancora stata ritirata.
Diamo ora un'occhiata a come implementare i loop in Ansible.
Esecuzione su semplici loop
Considera un Playbook che aggiunge un nuovo utente al sistema di destinazione utilizzando il modulo utente come mostrato:
--- - hosts: ubuntu_webserver tasks: - name: Create new user john user: name: john state: present
Questo sembra a posto. Ma cosa succede se abbiamo più utenti da aggiungere al sistema di destinazione? Come lo faremmo? Un modo sarebbe duplicare le attività come mostrato nell'esempio seguente in cui stiamo aggiungendo 3 utenti.
--- - hosts: ubuntu_webserver tasks: - name: Create new user john user: name: john state: present - name: Create new user mike user: name: mike state: present - name: Create new user andrew user: name: andrew state: present
Come puoi sembrare, questo richiede molte duplicazioni e ripetizioni.
Per semplificare le cose, lo stesso playbook può essere scritto usando la direttiva loop. La direttiva loop esegue la stessa attività più volte. Memorizza il valore di ogni articolo in una variabile chiamata item .Quindi, invece di specificare i nomi degli utenti da aggiungere, è sufficiente specificare una variabile denominata item racchiusa tra doppie parentesi graffe come mostrato.
nome:'{{ item }}'
Pertanto, ciascuno degli elementi all'interno del ciclo sarà referenziato dalla variabile.
Come puoi vedere, il nostro playbook ora è molto più organizzato con inutili duplicazioni/ripetizioni.
$ vi create_users.yaml --- - hosts: ubuntu_webserver tasks: - name: Create new users user: name: '{{ item }}' state: present loop: - john - mike - andrew
Inoltre, puoi utilizzare with_items direttiva invece della direttiva loop. Entrambi produrranno lo stesso risultato.
--- - hosts: ubuntu_webserver become: yes tasks: - name: Create new users user: name: '{{ item }}' state: present with_items: - john - mike - andrew
Ora puoi eseguire il playbook per creare gli utenti utilizzando ansible-playbook comando come mostrato di seguito:
$ ansible-playbook -i inventory.txt create_users.yaml
Iterazione su un elenco di dizionari
Nel primo esempio, abbiamo esaminato un semplice ciclo standard in cui l'array era un elenco di valori di stringa che rappresentano gli utenti da aggiungere alla destinazione remota.
Ma cosa succede se dobbiamo aggiungere l'uid al ciclo in modo tale che ogni elemento ora abbia due valori:il nome utente e uidi . Come passeresti 2 valori in un array?
In questo scenario, dovrai passare una matrice di dizionari, ciascuno con 2 coppie chiave-valore come mostrato. Le chiavi sarebbero il nome e l'uid mentre i valori saranno il nome utente e l'ID di ciascun utente.
Sotto le "attività ', non è più possibile definire la variabile item come prima. Poiché abbiamo 2 valori, questo si tradurrà in due variabili:nome.oggetto &item.uid .
Il playbook completo è mostrato di seguito:
$ vi create_users.yaml --- - hosts: ubuntu_webserver become: yes tasks: - name: Create new users user: name: '{{ item.name }}' uid: '{{ item.uid }}' state: present loop: - name: john uid: 1020 - name: mike uid: 1030 - name: andrew uid: 1040
L'array di dizionari può anche essere rappresentato in un formato JSON.
loop: - { name: john , uid: 1020 } - { name: mike , uid: 1030 } - { name: andrew , uid: 1040}
Una volta eseguito, otterrai il seguente output:
$ ansible-playbook -i inventory.txt create_users.yaml
Ansible Loop con indici
Occasionalmente, potresti voler tenere traccia dei valori dell'indice all'interno della tua matrice di elementi. Per questo, usa "with indexed_items ' cercare. Il valore dell'indice inizia da 0 mentre l'indice del ciclo inizia da item.0 e il valore da item.1
Considera il playbook qui sotto:
$ vi indexes.yaml --- - hosts: ubuntu_webserver tasks: - name: Indexes with Ansible loop debug: msg: "The car at {{ item.0 }} is {{ item.1 }}" with_indexed_items: - "Nissan" - "Mercedes" - "Toyota" - "Mazda" - "BMW"
Quando viene eseguito, il playbook mostra il valore di indice di ogni elemento nell'elenco di array.
$ ansible-playbook -i inventory.txt indexes.yaml
Condizionali in Ansible Loops
In Ansible loop è possibile utilizzare l'istruzione condizionale quando si controlla il loop in base alla natura delle variabili o dei fatti di sistema. Considera il playbook di seguito in cui abbiamo un elenco di pacchetti che devono essere installati.
Abbiamo specificato un array chiamato "pacchetti ' che contiene un elenco di pacchetti che devono essere installati. Ciascuno degli elementi dell'array contiene il nome del pacchetto da installare e la proprietà denominata "richiesto ' che è impostato su 'Vero ' per 2 pacchetti e 'Falso 'per un pacchetto.
$ vi install-packages.yaml --- - name: Install software become: yes hosts: all vars: packages: - name: neofetch required: True - name: cpu-checker required: True - name: screenfetch required: False tasks: - name: Install "{{ item.name }}" on Ubuntu apt: name: "{{ item.name }}" state: present when: - item.required == True - ansible_facts['distribution'] =="Ubuntu" loop: "{{ packages }}"
Il "quando ' istruzione condizionale cerca di installare i pacchetti software con la proprietà 'richiesto ' impostato su 'Vero ' su sistemi di destinazione che sono distribuzioni Ubuntu. Di seguito è riportato l'output del playbook una volta eseguito.
L'output dettagliato mostra chiaramente i pacchetti che vengono installati e quello che viene ignorato in base all'istruzione condizionale.
E questo ci porta alla fine di questo argomento. Ci auguriamo che tu abbia una comprensione decente dei loop nei playbook di Ansible. Non esitare a contattarci per qualsiasi chiarimento.
Leggi anche :Come utilizzare il modello Jinja2 in Ansible Playbook