Ansible: Necessity of running multiple playbooks? - ansible

Owing to needing some dependencies from ansible-galaxy, and other installed software such as ssh-pass, I can't find a way around having to run multiple playbooks sequentially.
Is there a way around this, or is this a feature to be added in future? I've seen it suggested that multiple playbooks may be put in a shell script but surely this is a job for a configuration management program such as ansible?

You can use import_playbook which is merely an import without any other functionality. For example the three playbooks below
shell> cat playA.yml
- hosts: localhost
tasks:
- debug:
msg: Play A
shell> cat playB.yml
- hosts: localhost
tasks:
- debug:
msg: Play B
shell> cat playC.yml
- hosts: localhost
tasks:
- debug:
msg: Play C
can be put into one playbook
shell> cat playABC.yml
- hosts: localhost
tasks:
- debug:
msg: Play A
- hosts: localhost
tasks:
- debug:
msg: Play B
- hosts: localhost
tasks:
- debug:
msg: Play C
, or can be imported into one playbook
shell> cat playABC-import.yml
- import_playbook: playA.yml
- import_playbook: playB.yml
- import_playbook: playC.yml
Both options give the same result. If you need smarter control of the playbooks use ansible-runner.

Related

How can I specify hosts when importing a playbook

ansible version: 2.9
Hi.
How can I specify the hosts when I import a playbook with import_playbook?
My code (/project/first_pb.yml)
- import_playbook: /test/pb0.yml
hosts: atlanta
Q: "A method to pass specific family hosts to the imported playbook?"
A: There is no difference between a playbook imported or not. For example,
shell> cat pb-A.yml
- hosts: "{{ my_hosts|default('localhost') }}"
tasks:
- debug:
var: inventory_hostname
shell> ansible-playbook pb-A.yml -e my_hosts=host1
...
inventory_hostname: host1
shell> cat pb-B.yml
- import_playbook: pb-A.yml
shell> ansible-playbook pb-B.yml -e my_hosts=host1
...
inventory_hostname: host1
There are many options on how to pass specific hosts and groups to a playbook. For example, see:
Patterns: targeting hosts and groups
add_host module – Add a host and group to the ansible-playbook in-memory inventory
Inventory plugins (e.g. constructed)
I can filter play plabooks with "when: " condition, for example:
- import_playbook: /test/pb0.yml
when: hostname != host1a*
- import_playbook: /test/pb0.yml
when: '"north" not in hostname'
- import_playbook: /test/pb0.yml
when: '"west" in hostname'

Run tasks on different hosts within an imported task

The calling playbook has:
- hosts: ssh_servers
tasks:
- import_tasks: create_files.yml
Then, in create_files.yml, I'd like to run some tasks on hosts other than ssh_servers, such as:
- Hosts: other_servers
tasks:
- file:
I get: ERROR! conflicting action statements: hosts, tasks .
Is this because I'm trying to run against hosts that were never included in the calling task ?
Is there a way to accomplish this other than in the calling playbook have:
- hosts:
- ssh_servers
- other_servers
tasks:
- import_tasks: create_files.yml
Thank you.
Is this because I'm trying to run against hosts that were never included in the calling task ? Is there a way to accomplish this other than in the calling playbook
I believe the answer is yes, although it'll be weird and could cause subsequent folks who interact with your playbook some confusion
given a hypothetical create_files.yml of:
- name: create /tmp/hello_world on hosts "not_known_at_launch_time"
file:
path: /tmp/hello_world
state: present
delegate_to: '{{ item }}'
with_items: '{{ groups["not_known_at_launch_time"] }}'
then the glue needed to bridge them together is the dynamic creation of a group and that delegate_to: keyword
- hosts: ssh_hosts
tasks:
- add_host:
groups: not_known_at_launch_time
name: secret-host-0
ansible_host: 192.168.1.1 # or whatever
# ... other hostvars here ...
- include_tasks: create_files.yml
it may be possible to combine those inside create_files.yml, via some shared vars: that say which host-and-ip should be added to the magic group name, which also has the benefit of keeping the magic group name localized to the file that consumes it.
BE AWARE, I did actually test this, but not extensively, so there may be some weird things such as the need to run_once: yes on them to keep the tasks from being run groups.ssh_hosts|length times or similar stuff
As Vladimir correctly pointed out, what you actually want to happen is to make that relationship formal:
- hosts: ssh_hosts
tasks:
... whatever tasks you had before
- add_host: ... as before ...
- hosts: anonymous_group_name_goes_here
tasks:
- include_tasks: create_files.yml
- hosts: ssh_hosts
tasks:
- debug:
msg: and now you are back to the ssh_hosts to pick up what they were supposed to be doing when you stopped to post on SO

How to detect --limit in ansible playbook?

I have a task which has meaning only if it has been run with full list of hosts (creating a /etc/ssh/ssh_known_hosts file). I want to skip this task if '--limit' has been used.
Is any way in ansible to detect if --limit option was used?
After some struggles I found a way:
- hosts: all
gather_facts: no
tasks:
- set_fact:
full_run: '{{play_hosts == groups.all}}'
...
- hosts: other_group
tasks:
- template: ...
when: full_run

ansible generate *.retry file error when there are multiple plays in playbook

For example, deploy.yml is a ansible playbook. There are two plays in deploy.yml, play1 and play2.
$ cat deploy.yml
- hosts: nodes
remote_user: cloud
become: yes
tasks:
- name: play1
copy: src=test1 dest=/root
- hosts: nodes
remote_user: cloud
become: yes
tasks:
- name: play2
copy: src=test2 dest=/root
$ cat hosts
[nodes]
192.168.1.12
192.168.1.13
Running
ansible-playbook -i hosts deploy.yml
When play1 failed on 192.168.1.12 but success on 192.168.1.13, the deploy.retry only list 192.168.1.12 but no 192.168.1.13.
$ cat deploy.retry
192.168.1.12
Then I running
ansible-playbook -i hosts deploy.yml --limit #deploy.retry
I got a wrong result of play2 haven't be running on 192.168.1.13! Some people know how to solve this problem?
Problem is in playbok file, in facts, you have two independent playbooks in one file. I tested your setup with ansible 2.2.1.0 and second play run correctly for host without error in play1, but there can be difference in configuration.
Correct playbook format for expecting behavior is
- hosts: nodes
remote_user: cloud
become: yes
tasks:
- name: play1
copy: src=test1 dest=/root
- name: play2
copy: src=test2 dest=/root

can ansible run multiple playbooks same time?

- name: "API"
hosts: api
vars:
platform: "{{ application.api }}"
vars_files:
- vars/application-vars.yml
tasks:
- include: tasks/application-install.yml
- name: "JOBS"
hosts: jobs 
vars:
platform: "{{ application.jobs }}"
vars_files:
 - vars/application-vars.yml
tasks:
  - include: tasks/application-install.yml
playbook like before described, can I execute this difference tasks on difference hosts in the same time as parallel way?
No sure what do you actually want, but I'd combine it into single play:
- hosts: api:jobs
tasks:
- include: tasks/application-install.yml
And add group vars to inventory:
[api:vars]
platform="{{ application.api }}"
[jobs:vars]
platform="{{ application.jobs }}"
This way you can run your playbook on all hosts at once, and also you can use --limit option to choose api or jobs group only.
you can run more playbooks using "ansible-playbook [OPTIONS] *.yml" command. This will execute all the playbooks NOT IN PARALLEL WAY, but in serial way, so first one playbook and after the execution, another playbook. This command can be helpful if you have many playbooks.
I don't know a way to execute more playbooks in parallel.

Resources