Updated May 12, 2023
Introduction to Ansible local_action
In Ansible, we always tend to work on remote target nodes, for which we write plays, tasks. This is a common understanding that anything written in a play and task will be executed on remoted target hosts unless specified otherwise. But many times you get a situation where you need to work on a local or controller machine to generate some data or do some modification, in between a playbook or in the middle of two tasks in a play. In such cases we need feature parameters like local_action, delegate_to, run_once are very useful. In this article, we will earn about Ansible local_action and ways to use it.
Explaining the Ansible local_action
Ansible has many feature parameters that are useful in such needs where you need to delegate a task to other hosts than the target remote host. Such parameters include local_action, delegate_to. When delegate_to is used to delegate a task on the local machine either using hostname localhost or IP 127.0.0.1, it’s the same as using the local_action parameter. We can use either of these.
This is useful as we can perform actions like sending mails between two tasks of updating packages and modifying relative configuration files and creating or modifying files locally before sending it to remote nodes.
How Does Ansible local_action Works?
In an Ansible playbook, when local_action is used, Ansible will run the module work mentioned under it on the controller node. Mostly modules used with local_action are shell and command. As you can do almost all the tasks using these modules on the controller node.
---
# ...
tasks:
- name: a sample module
local_action: command <command to execute>
But even if you want to use an Ansible module to work locally, you can use it like below: –
---
# ...
tasks:
- name: sample module local_action:
module: <module name>
<....module parameter...>
<....other feature parameters >
We will see some of the possible ways to use it in the next section using some examples. But you must note the syntax and indentations to be used.
Examples
Now by using examples, we will try to learn about Ansible feature parameter local_action along with some other useful parameters, which you might have to use in day to day operations. We will take some examples, but before going there, we first understand our lab, we used for testing purpose.
Here we have an Ansible controller server named ansible-controller and two remotes hosts named host- one and host-two. We will create playbooks and run Ansible commands on the ansible-controller node and see the results on remote hosts.
In this example, we have created a playbook with contents like below, here we are trying to achieve that when we use local_action, a file will be created in controller node and the afterward, this will be copied to the remote target
---
hosts: all tasks:
name: This will create a local file /tmp/local_file.ini.
local_action: command touch /tmp/"{{ ansible_hostname }}"_local_file.ini
name: Here we copy the local file to remote copy:
src: /tmp/{{ ansible_hostname }}_local_file.ini dest: /var/tmp/
Executing the playbook using below command: –
ansible-playbook ansible_local_action_create_file.yaml -v
Give the output like below: –
Here we can see that when playbook ran, copied a file on remote target nodes, this file was created in the task where local_action is mentioned and this was performed on local machine viz. the Ansible controller node.
ll /tmp/*_local_file.ini
In this example, we have created a playbook with contents like below, here we are trying to achieve to do Rsync directory /tmp on the controller node to remote
---
hosts: all tasks:
name: recursively copy files in /tmp contoller node to remote local_action: command rsync -a /tmp {{ ansible_hostname }}:/tmp
Executing the playbook using below command: –
ansible-playbook ansible_local_action_rsync.yaml -v
Give the output like below: –
Here we can see that when playbook ran, it did rsync on remote target nodes with the controller node in the task where local_action is mentioned and performed on local machine viz. the Ansible controller node.
In this example, we have created a playbook with contents like below, here we are trying to achieve that when we are updating a package on remote machines, a mail should be sent to an email account, with a mail body and subject, so that that mail owner is notified of the changes. Also note the use of run_once, which make the sending mail to execute only
---
hosts: all tasks:
name: Send summary mail local_action:
module: mail
subject: "Summary Mail" to: root@localhost
body: we are installing or updating the httpd run_once: True
name: Update the remote machines. yum:
name: httpd state: latest
Executing the playbook using below command: –
ansible-playbook ansible_local_action_mail_update.yaml
Give the output like below: –
Here we can see that when playbook ran, it did try to upgrade httpd package on remote target nodes and the mailing task where local_action is mentioned was performed on local machine viz. the Ansible controller node. Also, it was performed only once, as we have used run_once.
We can check that if the mail was created and sent, to check that we have mailx utility. Using this we can read mail like below: –
mailx
In this example, we have created a playbook with contents like below, here we are trying to achieve that in a cluster of servers working behind a load balancer. To avoid downtime, we make a server out of the cluster and update it and then add back to the cluster
---
hosts: web_servers tasks:
name: make a server out of LB pool
local_action: command: /script_to_take_out {{ inventory_hostname }}
name: update the relevant package yum:
name: package to update state: latest
deleagte_to: {{ inventory_hostname }}
name: add back the server to LB pool
local_action: command: /script_to_add {{ inventory_hostname }}
We can replace the above sample with real-life values and use them. The task which has delegate_to will run on the machine which is mentioned after it.
Conclusion
As we saw, using local_action is a bit tricky, but it can help you to overcome the problem of running multiple playbooks for simple tasks that involve the localhost or controller machine along with target remote machines. Also, as you saw in examples, using it with other feature parameters like run_once makes it more sensible to use. So learn it first and then use it.
Recommended Articles
This is a guide to Ansible local_action. Here we discuss how does Ansible local_action works along with commands and respective examples. You may also look at the following articles to learn more –