Definition

Let’s say we have a static inventory with 10 hosts, but we know for sure that some of these hosts will be unavailable

Of course, we can use a dynamic inventory and do ansible.builtin.meta: refresh_inventory during playbook execution

But this will be true only when running via CLI (ansible-playbook/ansible-navigator/ansible), AWX/AAC does not support ansible.builtin.meta:refresh_inventory (see https://github.com/ansible/awx/issues/7276) and also does not support passing extra_vars to dynamic inventory (see https://github.com/ansible/awx/issues/13004)

In simpler cases, the ability to use jinja directly in the hosts: field of the play will help, for example:

- name: Install FreeIPA
  hosts: "{{ 'freeipa_hosts' if deploy_freeipa else 'none' }}"
  become: true
  tasks:
    ...

That is, if the value of deploy_freeipa is true at the global level, then the task will be executed, and if not, then it will be skipped

However, it is often convenient to use the all group to execute tasks on all hosts from the inventory, which is impossible in our case (we will access non-existent hosts and get the UNREACHABLE error), as an option - use ignore_unreachable: true, but then you will have to spend time waiting in each play task

Within one play you can do this:

- name: Configure DNS on all hosts
  hosts: all
  gather_facts: false
  become: true
  tasks:
    - name: Remove unused hosts
      block:
        - name: Remove unused hosts
          ansible.builtin.wait_for_connection:
            timeout: 30
      rescue:
      # The task below is needed so that the result of the playbook execution is not considered FAILED
        - name: Clean errors from them
          ansible.builtin.meta: clear_host_errors

        - name: End play for these hosts
          ansible.builtin.meta: end_host
      ...

In this case, unavailable hosts will simply be removed from this play, but what if there are several such plays?

Then you can create a group of unavailable hosts and use host patterns in subsequent plays (link leads to a post)

- name: Configure DNS on all hosts
  hosts: all
  gather_facts: false
  become: true
  tasks:
    - name: Remove unused hosts
      block:
        - name: Remove unused hosts
          ansible.builtin.wait_for_connection:
            timeout: 30
      rescue:
        - name: Create host group for failed host
          ansible.builtin.group_by:
            key: failed_hosts

        # The task below is needed so that the result of the playbook execution is not considered FAILED
        - name: Clean errors from them
          ansible.builtin.meta: clear_host_errors

        - name: End play for these hosts
          ansible.builtin.meta: end_host
    ...

- name: Configure HOSTNAME on all hosts
  hosts: all:!failed_hosts
  gather_facts: false
  become: true
  tasks:
    ...