# Patching cluster servers

**URL:** <https://forum.ansible.com/t/patching-cluster-servers/242>\
**Category:** Get Help\
**Tags:** windows, cluster, playbook, linux\
**Created:** [September 1, 2023, 1:04pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242 "2023-09-01T13:04:58Z")\
**Posts on this page:** 10\
**Page:** 1

<div class="post-metadata">

**Author:** ![horner](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/horner/32/203_2.png) [@horner](https://forum.ansible.com/u/horner)\
**Post date:** [September 1, 2023, 1:04pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/1 "2023-09-01T13:04:59Z")

</div>

Hello everyone!

I am using Ansible to patch Linux and Windows servers. It is working well to patch servers that are not part of a cluster. But I can’t make it work to patch clusters.

Those are my requirements:

- Start patching simultaneously all servers that are not part of any cluster.
- Start patching N servers on all clusters simultaneously and patch all remaining servers on each cluster when the first N servers finish patching successfully.

I’ve tried to accomplish this grouping hosts by cluster. I used ‘single’ to group all servers not part of any cluseter. I’ve used multiple ansible.builtin.import\_playbook on a main play. One import would handle ‘single’ servers using free strategy. I’ve also added one extra import for each cluster and for them strategy would be linear with N and 100% serial, to patch N servers simultaneously first and after patching those servers is done successfully the remaining would be patched simultaneously.

Problem is I can’t setup ansible.builtin.import\_playbook to run asynchronously. It will wait all single server execution before starting running cluster imports.

Is there a way to accomplish this with Ansible?

Does anyone have any other solution to patch servers on multiple clusters using Ansible?

Thank you!

---

<div class="post-metadata">

**Author:** ![IPvSean](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/ipvsean/32/1153_2.png) [@IPvSean](https://forum.ansible.com/u/IPvSean)\
**Post date:** [September 1, 2023, 1:21pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/2 "2023-09-01T13:21:22Z")

</div>

so lets imagine there is three groups based on your description:

- no\_cluster
- A\_cluster
- B\_cluster

So you want no\_cluster and A\_cluster to run at the same time, you would just do this-\>

```auto
- name: wait for all nodes to have SSH reachability
  hosts: "no_cluster:A_cluster"
  tasks:
    blahblahblah

```

then immediately below this play, you just have a 2nd play:

```auto
- name: wait for all nodes to have SSH reachability
  hosts: "B_cluster"
  tasks:
    blahblahblah

```

the default behavior will be to run each play in parallel, so this “should” get you what you want behavior wise in the simplest “ansible”-way I can think of.

There is also ways to control the _strategy_ in Ansible… [Controlling playbook execution: strategies and more — Ansible Documentation](https://docs.ansible.com/ansible/latest/playbook_guide/playbooks_strategies.html)

but I don’t think you need to do this if I understand your use-case. You can also use [async](https://docs.ansible.com/ansible/latest/playbook_guide/playbooks_async.html)… but I highly recommend against this.

Finally… I am trying to solve your problem with cli-Ansible but creating parallel automation jobs is something that automation controller (product part of Ansible Automation Platform) or the upstream project AWX can do really well. You basically would use a [workflow here](https://docs.ansible.com/automation-controller/latest/html/userguide/workflows.html).

---

<div class="post-metadata">

**Author:** ![horner](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/horner/32/203_2.png) [@horner](https://forum.ansible.com/u/horner)\
**Post date:** [September 1, 2023, 1:48pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/3 "2023-09-01T13:48:26Z")

</div>

Thank you for your message Sean.

Adding 2 groups on the same include/task list would make they all use the same strategy, right?

By doing that I will not be able to use free strategy for no\_cluster and linear to A\_cluster.

I have a role with tasks to make checks, create snapshots, do the patching and post logs.

I think to achieve what I need I should start 3 calls to the same role simutaneously:

- no\_cluster with free strategy
- A\_cluster with linear strategy considering only hosts of this group
- B\_cluster with linear strategy considering only hosts of this group

This way patching of all groups would start simultaneously but no\_cluster will patch all at the same while A\_cluster and B\_cluster will patch N servers simultaneously and all other servers after the first set is done.

---

<div class="post-metadata">

**Author:** ![IPvSean](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/ipvsean/32/1153_2.png) [@IPvSean](https://forum.ansible.com/u/IPvSean)\
**Post date:** [September 1, 2023, 2:29pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/4 "2023-09-01T14:29:38Z")

</div>

I don’t think you need the strategy at all, the default strategy is to run in parallel, I probably shouldn’t have linked this at all because in your specific situation it is not needed.

I also think you mis-understood my A\_cluster and B\_cluster. I didn’t intend to show two different clusters, but part A and part B. Does that make sense?

If you have 3 groups of servers, you have “servers that don’t belong to any cluster”, so they can be patched simultaneously with “half” of the servers that are in the cluster. This is what I “think” you want. You would do what I showed above, just understand that A\_cluster is just part A of your cluster. I think names are hard…

---

<div class="post-metadata">

**Author:** ![horner](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/horner/32/203_2.png) [@horner](https://forum.ansible.com/u/horner)\
**Post date:** [September 4, 2023, 4:28pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/5 "2023-09-04T16:28:34Z")

</div>

Hello Sean,

Yes, this is what I am trying to do:

> If you have 3 groups of servers, you have “servers that don’t belong to any cluster”, so they can be patched simultaneously with “half” of the servers that are in the cluster. This is what I “think” you want. You would do what I showed above, just understand that A\_cluster is just part A of your cluster. I think names are hard…

Only thing is there are multiple clusters to be patched, and I need the installation on each cluster to stop if there are any error on servers of first batch ot the respective cluster.

To achieve that I think it would be easier to have one linear strategy execution for each cluster. I would like to achieve that with a single Ansible run, but I don’t think it is possible to have like I described: 1 free execution and N linear executions, all starting at the same time.

When using subsequent play/task calls like you suggested, the servers on the second batch will need to know all servers that are part of the same cluster and check patching results of those server to throw execption if there errors on any of them.

---

<div class="post-metadata">

**Author:** ![IPvSean](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/ipvsean/32/1153_2.png) [@IPvSean](https://forum.ansible.com/u/IPvSean)\
**Post date:** [September 5, 2023, 1:32pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/6 "2023-09-05T13:32:21Z")

</div>

so imagine you have 3 clusters, each with 4 servers each (just for illustration purposes) and 2 servers that belong to no clusters. Look at the below diagram:

 ![image](https://us1.discourse-cdn.com/ansible/original/1X/70a1fd1510f503d9b906145634ae496464095925.png)

The groups defined above are in the INI format, but you can use YAML as well if you prefer.

To run simultaneously in parallel, all the A groups AND no cluster servers it would simply be an Ansible Playbook **Play** that defines all those groups, THEN it would do the B\_group in the second play-\>

```auto
- name: run automation for nocluster and all A_group servers
  hosts: "nocluster:A_group"
  tasks:
    blahblahblah
- name: run automation for all B_group servers
  hosts: "B_group"
  tasks:
    blahblahblah

```

Everything in group\_A would finish before it started group\_B given the above Play stanzas

Does that make sense and help?

---

<div class="post-metadata">

**Author:** ![horner](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/horner/32/203_2.png) [@horner](https://forum.ansible.com/u/horner)\
**Post date:** [September 5, 2023, 7:29pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/7 "2023-09-05T19:29:50Z")

</div>

Yes, that makes sense, and it almost works.

Only problem is it doesn’t address errors patching cluster servers.

Considering your example, let’s say Cluster 1 is a DB server cluster, we would like to check patching result on each server before moving to second set of servers because if installing new patches break something we still have working servers and can restore backups of broken servers to restore the whol cluster.

Having two separate plays make servers on them unrelated, right?

---

<div class="post-metadata">

**Author:** ![IPvSean](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/ipvsean/32/1153_2.png) [@IPvSean](https://forum.ansible.com/u/IPvSean)\
**Post date:** [September 5, 2023, 7:50pm UTC](https://forum.ansible.com/t/patching-cluster-servers/242/8 "2023-09-05T19:50:20Z")

</div>

> [@horner](#):
>
> Having two separate plays make servers on them unrelated, right?

Correct. If an individual server fails, the automation will stop for that host alone. Ansible would need more information to know how hosts are inter-related.

You could check if whatever group/server ran, then you could run something else, but this would require multiple tasks in your Ansible Playbooks can could be quite hard to understand and quickly become “unAnsibley”, which is to say unwieldy. I would highly recommend if you need this sorta complexity to consider the community project AWX (or our product Ansible Automation Platform) and use the `workflow` feature. This allows you to quickly drag and drop a playbook but you can decide if the next “job” runs if the previous job runs: [23. Workflows — Automation Controller User Guide v4.5](https://docs.ansible.com/automation-controller/latest/html/userguide/workflows.html)

Look at the screenshot from the documentation:

 ![image](https://us1.discourse-cdn.com/ansible/original/1X/2f0b1759ecfd6b614879b8a7bc8ade7c2b3e6170.png)  
Each of these rectangles is the equivalent of an Ansible Playbook. A red line means “run this job only if the previous job failed”, a green line means “run this job only if the previous job passed” and a blue line means “always run this job”.

This way you can drag and drop, a very simple playbook, without too much complexity, and then make judgement calls that may get increasingly complex. If the “database cluster group A” fails, then run this job, “if it passes”, then run this job.

Does that make sense? Otherwise your playbook is going to get really jumbly really quick with all the corner cases of what server needs to be patched before some other server.

If you can only use command-line Ansible, if its just a handful of servers that have odd requirements, you can just use set\_fact or register the result of a task and then have a subsequent task only run if that previous one passed.

---

<div class="post-metadata">

**Author:** ![gwmngilfen](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/gwmngilfen/32/6_2.png) [@gwmngilfen](https://forum.ansible.com/u/gwmngilfen)\
**Post date:** [September 15, 2023, 10:48am UTC](https://forum.ansible.com/t/patching-cluster-servers/242/9 "2023-09-15T10:48:14Z")

</div>

Hi @horner! It looks like the post might be solved - could you check to see if the response by @IPvSean worked for you?

If so, it would be _super_ helpful if you could click the ✔ on their post to accept the solution - it recognises the input of others, helps our volunteers find new issues to answer, and keeps the forum nice and tidy.

Thanks!  
(this is template reply, do feel free to reply if I’ve misunderstood the situation!)

---

<div class="post-metadata">

**Author:** ![gwmngilfen](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/gwmngilfen/32/6_2.png) [@gwmngilfen](https://forum.ansible.com/u/gwmngilfen)\
**Post date:** [October 15, 2023, 10:49am UTC](https://forum.ansible.com/t/patching-cluster-servers/242/10 "2023-10-15T10:49:03Z")

</div>

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.
