How to Install and Configure Ansible on Ubuntu (Part 1)

Ansible is a Configuration Management and Application Deployment system that is designed to streamline the process of controlling a large number of servers, basically for administration and operational processes. In other words, it allows you to control several remote machines in an automated fashion from a location.

Ansible uses an SSH channel for communication to control the remote machines/servers. Hence, any system that has an open an SSH port can be configured by an Ansible machine, also known as Ansible Control Node. It works on a modular approach: modules can be on any language and communicate in standard JSON.

There are two different ways through which Ansible can interact with the remote host or machine, either via command line tools or its configuration scripts, which are mainly written in the .YAML format, widely known as Playbooks.

Before we begin this tutorial, the requirements are as follows:

  1. A machine that will act as an Ansible Control Node, which will be used to connect and control the remote machines/servers. Control Node can either be your local machine or a designated secure Ansible server on Ubuntu 18.04.
  2. A non-root user with sudo privileges
  3. One or more remote hosts, which will be configured to automate via your Ansible Control Node. Please make sure that the control node has SSH access to the systems/machines/servers.

Installing Ansible on the Machine

You can install Ansible either on a local machine or designate a specific machine that is going to act as a Control Node for administrators and operation teams.

There are multiple ways through which you can install the Ansible on your system, here we are going to discuss two of them: PPA (preferred) and from the source code.

Installing via PPA (Personal Package Archive):

First, you have to include the official project’s PPA into your system by running the following command:

$ sudo apt update && sudo apt-add-repository -y --update ppa:ansible/ansible

To make sure that the system is aware of the packages, again, refresh your machine’s package index:

$ sudo apt update

Now your machine is ready to install Ansible; you can install it by running the following command:

$ sudo apt install ansible -y

You can verify the installation by this command:

$ ansible --version
ansible 2.5.1
 config file = /etc/ansible/ansible.cfg
 configured module search path = [u'/home/gaurav/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
 ansible python module location = /usr/lib/python2.7/dist-packages/ansible
 executable location = /usr/bin/ansible
 python version = 2.7.17 (default, Nov  7 2019, 10:07:09) [GCC 7.4.0]

Installing via Source Code:

Many users prefer to install Ansible for the source code as they can get their hands on the latest features on the fly, there is no software to install, no demons nor database setup is required. Hence there are very slim chances of anything wrong. However, you shouldn’t go this path because if you get into some error or issue, then troubleshooting can take a heavy toll if you are new to the Ansible realm.

$ cd ~
$ git clone && cd $_

Once you have cloned the repo, set up the Ansible environment using Bash:

$ source ./hacking/env-setup

Alternatively, you can use the MAKE command:

$ make
$ sudo make install

You can verify the installation by this command:

$ ansible --version
ansible 2.5.1
 config file = /etc/ansible/ansible.cfg
 configured module search path = [u'/home/gaurav/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
 ansible python module location = /usr/lib/python2.7/dist-packages/ansible
 executable location = /usr/bin/ansible
 python version = 2.7.17 (default, Nov  7 2019, 10:07:09) [GCC 7.4.0]

Now, as your machine is ready to perform administrative activities on your host system, the next step is to add your host system to the control node’s inventory file.

Setting Up Control Node’s Inventory File:

In simple words, the inventory file consists of information about the host machines/systems/server that you are going to manage with Ansible. There is absolutely no restriction that how many hosts you can add to your control node, as hosts can be organized into smaller groups and sub-groups as per your organization structure or system requirement, which later will be used within your playbooks and template.

In the inventory file, you might often have to set various variables, which governs how your playbook is going to run; for example, ansible_python_interpreter is one of those variables which you are going to use every often.

You can find the Ansible inventory file at /etc/ansible/hosts. Go to your terminal and choose editor of your choice on your Control Node:

$ sudo nano /etc/ansible/hosts

Note that on some occasions, during installation, Ansible won’t create a default inventory file. In case if you don’t find one on your system, then feel free to create a new one for yourself at /etc/ansible directory.

Although you can choose any desired location to create your inventory file, if that is the case, then you need to specify the custom inventory path by using the parameter -i during running commands and playbooks.

By default, Ansible installation provides you with many cases that you can use as a reference for setting up your inventory file. However, we are going to set up our own group and sub-group; for this, we are going to define three different servers under group name [myremote] and sub-group name [myremote:vars] where we are going to set variable. Please make sure that you replace the IP addresses of your Ansible hosts in remote1, remote2, and remote3.

remote1 ansible_host=
remote2 ansible_host=
remote3 ansible_host=333.333.333.333

You might have noticed that we are using ansible_python_interpreter in our myremote:vars sub-group as the host parameter, which will be invoked for all our hosts specified under myremote group. The reason you are using Python 3 executable is because Python 2.7 is not present on recent Ubuntu versions.

You can see the changes done to your inventory files by running the following command:

$ ansible-inventory --list -y
         ansible_python_interpreter: /usr/bin/python3
         ansible_python_interpreter: /usr/bin/python3
         ansible_host: 333.333.333.333
         ansible_python_interpreter: /usr/bin/python3
   ungrouped: {}

Setup SSH Keys

SSH keys are the safest way to ensure that your connection remains secure, and also, you won’t be facing issues while connecting the Ansible hosts.

To generate the key, you can do this:

$ ssh-keygen -f ~/.ssh/ -t rsa -b 4096

Now you have to copy the ssh key to your Ansible hosts that are remote1, remote2, and remote3. Before running the ssh-copy command, make sure that you have access to your remote servers. To copy the key to your remote host, use this command;

For remote1:

$ ssh-copy-id -i ~/.ssh/ root@

For remote2:

$ ssh-copy-id -i ~/.ssh/ root@

For remote3:

$ ssh-copy-id -i ~/.ssh/ root@333.333.333.333

Now it’s time to test whether our Ansible control node can connect with remote hosts.

Testing Connection from Your Ansible Control Node

We are now going to test our connection with user root, although you can specify a regular sudo user by using -u argument.

Command ping is a built-in Ansible module, which helps to run a connectivity test on all the nodes that are defined in your inventory file as user root.

$ ansible all -m ping -u root
remote1 | SUCCESS => {
   "changed": false,
   "ping": "pong"
remote2 | SUCCESS => {
   "changed": false,
   "ping": "pong"
remote3 | SUCCESS => {
   "changed": false,
   "ping": "pong"

This is the first time you are connecting to the remote host via SSH; hence, you will be asked to confirm the authenticity of the hosts you are connecting to via Ansible. Prompt will occur in the terminal, type ‘yes’, and then hit ENTER.

In response to ping, you will receive a “pong” for the host; it confirms that your control node is ready to run the commands and playbook s on that particular host.

Running Ad-Hoc Commands

As your Ansible setup is completed, you can now start running ad-hoc commands and playbooks on your server.

An Ansible Ad-hoc commands use the /usr/bin/ansible command-line tool, which automates a single task on your remote servers. Ad-hoc commands are used for a quick task as we used above ansible all -m ping, but you can not replace it with playbooks as they are not reusable; as you advance in Ansible, you will rarely use it.

An Ad-Hoc command looks like this:

$ ansible [pattern] -m [module] -a “[module options]”

As an example, you can check the username on all servers with:

$ ansible all -m shell -a ‘whoami’
remote1 | SUCCESS | rc=0 >>
remote2 | SUCCESS | rc=0 >>
remote3 | SUCCESS | rc=0 >>

Alternatively, you can also run the shell module for a single user, like this:

$ ansible remote1 -m shell -a ‘whoami’
remote1 | SUCCESS | rc=0 >>

You can always run more about patterns and modules from the Ansible user guide.


In this guide, you’ve installed Ansible, while setting up an inventory file which helped you to run Ad-Hoc commands so that you can perform certain operations on your remote machines.

In the next part of this series, we are going to use Ansible to install and setup Docker, where you can learn how to write your own playbooks.

Subscribe and discover the newest
updates, news, and features

We value your inbox and are committed to preventing spam