wake-up-neo.com

Übergeben Sie Ansible-Variablen von einer Rolle (die auf einem Host ausgeführt wird) an eine andere Rolle, die auf einem anderen Host im selben Playbook ausgeführt wird

Ich habe ein Playbook, das verschiedene Rollen auf verschiedenen Hosts ausführt. Ist es möglich, eine Variable von einer Rolle, die auf einem Host ausgeführt wird, an eine andere Rolle auf einem anderen Host zu übergeben, der innerhalb des gleichen Playbook-Laufs läuft? Oder eine Problemumgehung?

playbook
   Host1
     role1
       here I get some variables: var1 var2 ...etc
   Host2
     role2
       here I need to use var1 var2 ... etc from the above Host/role

Die Aufgabe in Rolle1, die die Variable db setzt, sieht folgendermaßen aus:

- Shell: cd /ACE/conf && grep ^db.url local1.properties | awk -F/ '{print $4}' | awk -F? '{print $1}'
  register: db

UPDATE: Auf dem ersten Host sind die Werte dynamisch, es ist wie eine Konfigurationsdatei, die immer aktualisiert wird. Nachdem ich die Werte in Variablen auf Host1 mit der Rolle1 gespeichert habe, gehe ich zum Host2, starte die Rolle2 und erledige diese Werte mit den von Host1 gespeicherten Variablen. 

Ich habe mit hostvars versucht:

{{ hostvars.LBL.db.stdout }}
{{ hostvars['LBL']['db'] }}
{{ hostvars['LBL']['db']['stdout'] }}

und ich bekomme Fehler:

in get_variables raise Exception("Host not found: %s" % hostname) Exception: Host not found: LBL

LBL ist in Hosts vorhanden, da ich die erste Rolle auf ihr ausführe

Ich setze eine Variable für einen Host und möchte, dass diese Variable für den anderen Host verfügbar ist. All dies in einem einzigen Spielbuch. Kann es gemacht werden

hostvars funktioniert nicht so:

---   
- name: test hostvars Host1
  hosts: LBL
  tasks:
    - command: "ls /bin"
        register: ls_out

- name: test hostvars Host2
  hosts: LM
  tasks:
    - debug:
        var: "{{ hostvars['LBL']['ls_out']['stdout'] }}"

error:

fatal: [10.104.148.138] => Host not found: LBL

/ etc/ansible/hosts

[[email protected] ansible]# cat /etc/ansible/hosts
[LBL]
10.104.148.136
[LM]
10.104.148.138
7
ady8531

Das Problem liegt in Ihrem Inventar.

Diese Nachricht: 

fatal: [10.104.148.138] => Host not found: LBL

ist weil LBL eine Gruppe und kein Host ist. Die Gruppe LBL enthält einen Host: 10.104.148.136

Führen Sie einen der folgenden Schritte aus:

1. Ändern Sie Ihren Bestand (/etc/ansible/hosts) in:

LBL ansible_ssh_Host=10.104.148.136
LM ansible_ssh_Host=10.104.148.138

2. oder wenn Sie wirklich wissen, was Sie tun, und LBL eine Gruppe ist und Sie dies beibehalten möchten, dann greifen Sie auf die Variable zu:

{{ hostvars['10.104.148.136']['db']['stdout'] }}

Wieder ist LBL eine Gruppe und kein Host. Mehr Info .

6
Kashyap

Dieses Thema ist kompliziert und es gibt zwei verschiedene Antworten, je nachdem, was Sie möchten.

Greifen Sie auf die Variable von einem Playbook auf den anderen Host zu

Beispiel:

---
- hosts: Host1
- roles:
    - role1
    - role2

Ziel: Sie möchten auf einige Variable von Rolle1 in Rolle2 zugreifen.

Set_fact-Modul verwenden.

Innere Rolle1:

name: save precious value
set_fact: 
  pantsu: shiroi

Inside Rolle2:

name: Nozoki...
debug: msg="Color is {{pantsu}}"

Zugriff auf statische Variablen für einen Host (oder eine Gruppe) für einen anderen

Beispiel:

[group_foo]
Host1
Host2
[group_bar]
Host3
Host4

group_vars/group_foo

important_value=bla-bla-ba

Ziel: Sie möchten es im Playbook für Gruppe2 verwenden.

Das ist viel schwieriger. 

Innerhalb von group_vars/group_bar

other_var: '{{hostvars[groups["group_foo"][0]].important_value}}'

Sie können außer '0' auch andere Indizes verwenden.

11
George Shuklin

Hier ist meine Lösung. Meine Aufgabe bestand darin, Daten zwischen zwei Servern zu synchronisieren, und ich wollte die Servernamen wie folgt weitergeben: ansible-playbook sync.yaml -e "source = Host1 destination = Host2"

Hier ist das Hauptbuch:

---

- name: get_sync_facts
  hosts: "{{ source }}"
  roles:
    - set_sync_facts

- name: sync
  hosts: "{{ destination }}" 
  roles:
    - get_sync_facts
    - sync

Hier ist die Rolle set_sync_facts:

---

- set_fact: src_media_dir='/some/dir/'
- set_fact: src_user='myuser'
- set_fact: src_Host='1.1.1.1'
- set_fact: src_port=12345
- set_fact: src_db_user='dbuser'
- set_fact: src_db_password='something'
- set_fact: src_db_name='some_db'

(Ich habe einige davon aus Aufgaben und andere von Host-Vars abgeleitet, aber Sie verstehen den Punkt)

Und hier ist die Rolle get_sync_facts:

---

- set_fact: src_media_dir={{ hostvars[source]['src_media_dir'] }}
- set_fact: src_user={{ hostvars[source]['src_user'] }}
- set_fact: src_Host={{ hostvars[source]['src_Host'] }}
- set_fact: src_port={{ hostvars[source]['src_port'] }}
- set_fact: src_db_user={{ hostvars[source]['src_db_user'] }}
- set_fact: src_db_password={{ hostvars[source]['src_db_password'] }}
- set_fact: src_db_name={{ hostvars[source]['src_db_name'] }}

Sie könnten darauf verzichten und nur Hostvars direkt in Ihren Spielen referenzieren, dies schien jedoch einfacher zu verwalten, da es direkt der Rolle set_sync_facts entspricht. 

2
Andy Baker

es ist ein ziemlich altes Thema, aber vielleicht wird es jemandem helfen. Ich habe sed verwendet, um den Hostnamen basierend auf "target" in zusätzlichen Parametern zu erhalten.

Um diese "Zielgruppe" zu verwenden, darf nur 1 Hostname enthalten.

Meine Inventar-Hosts:

[ansible_local]
localhost

[machine1]
machine1.domain.tld

upgrade_packages.yml

---
- hosts: '{{ target }}'
  Sudo: yes
  tasks:
  - name: check for Debian system
    Shell: /bin/false
    when: ansible_pkg_mgr != "apt"

  - name: full-upgrade all packages
    apt: update_cache=yes upgrade=full
    register: upgrade_result

- hosts: ansible_local
  tasks:
  - name: find out Host from target
    Shell: /bin/sed -n -e '/^\[{{ target }}\]$/,/^\[.*\]$/ { /^\[/d; /^$/d; p; }' {{ inventory_file }}
    register: target_inventory

  - name: Display all facts from target machine (change when to true if needed)
    debug: var=hostvars[target_inventory.stdout]
    when: false

  - name: Display upgrade result on ansible_local node
    debug: var=hostvars[target_inventory.stdout].upgrade_result.msg

Aufruf mit: ansible-playbook ./upgrade-packages.yml -e "target=machine1" -v

1
Quoing

Ich hatte ein ähnliches Setup, bei dem es drei Hosts h1, h2, h3 gibt, und auf jedem davon wollte ich eine Tatsache { "important_fact": "foo" } (bzw. bar und baz) definieren.

Um eine Liste mit allen verschiedenen wichtigen_Fakten auf allen Hosts zu erhalten, können Sie dies wie folgt tun:

- set_fact:
    important_facts_list: "{{ hostvars | json('*.important_fact') }}"
  run_once: yes
  delegate_to: h1

important_facts_list enthält [ 'foo', 'bar', 'baz' ], und Sie können sie jetzt mit with_items durchlaufen.

0