Ansible notes and quick start
Practical notes for using Ansible and quick start instruction
Published on updated on
For more information the official Ansible Documentation is invaluable.
The components of a basic Ansible environment are:
- control node is the host where Ansible is installed;
- inventory contains a list of the managed nodes;
- managed nodes the remote systems that are managed from a control node.
Article’s content:
Ansible installation on Ubuntu
Making a Debian/Ubuntu the control node means installing Ansible:
sudo apt update
sudo apt install software-properties-common
sudo apt install python3 python3-pip python3-venv python3-jmespath python3-psutil
sudo add-apt-repository --yes --update ppa:ansible/ansible
sudo apt install ansible ansible-lint
If a playbook requires additional collections:
# install the collections from a 'requirements.yml' file:
ansible-galaxy collection install -r requirements.yml
# installing a collection by name:
ansible-galaxy collection install <collection_name>
# upgrade all collections from a 'requirements.yml' file:
ansible-galaxy collection install --upgrade -r requirements.yml
# upgrade a single collection:
ansible-galaxy collection install --upgrade <collection_name>
Usage quick start, some explanations and notes
Generally ansible connects to the host with SSH.
It also needs SFTP but it can be restricted to use SCP instead with ANSIBLE_SCP_IF_SSH=True
option.
The best way to connect with SSH is to use the authentication with public/private key pairs, also shown in Getting started with Ansible but is not mandatory - after installing an OS, SSH may not be configured to use keys.
When you manage more the one server :) the best recommendation is:
- add the identity of your remote hosts to
~/.ssh/config
. See SSH Config File for information - add the remote hosts to an inventory file
- load private keys in
ssh-agent
while running Ansible commands
# list loaded keys
ssh-add -l
# add some keys
ssh-add <x_path_to_key_for_db_servers>
ssh-add <x_path_to_key_for_web_servers>
Remote host(s) specification
The -i, --inventory
flag specifies either:
- a comma separated host list - keep the last comma !
- an inventory file
Use the --limit
flag to limit the execution to a part of the inventory.
Use the --list-hosts
flag to only see the list of matching hosts, without executing anything else.
Examples:
-i 192.168.1.5,
-i 192.168.1.5,192.168.1.23,
-i web_servers.yml
-i inventories/development/web_servers.yml
# limit the execution to the hosts in the group 'internal_web_servers'
-i inventories/development/web_servers.yml --limit internal_web_servers
# limit the execution to the host 'web_servers_2'
-i inventories/development/web_servers.yml --limit web_servers_2
# limit the execution to the hosts that have names like 'web_servers_*'
-i inventories/test/servers.yml --limit web_servers_*
Inventory file example:
---
all:
hosts:
web_server_0:
ansible_host: 192.168.1.10
color: red
web_server_1:
ansible_host: 192.168.1.11
children:
internal_web_servers:
hosts:
web_server_0:
web_server_1:
vars:
color: blue
Example host identity in SSH config
Example host identity in ~/.ssh/config
:
Host web_server_1
HostName 192.168.1.11
User supervisor
IdentityFile ~/my_keys/web_servers
IdentitiesOnly yes
Authentication and authorization flags
-
-u, --user
specifies remote user. If this flag is omitted, searches~/.ssh/config
and, if user is not found, uses current user -
-k, --ask-pass
ask for remote user’s password -
--private-key
specify the private key for authentication -
--become-user
runs the commands / playbook as this user, default isroot
-
-K, --ask-become-pass
ask become password -
--become-method
privilege escalation method, defaultsudo
Ad-hoc commands
-m, --module-name
runs specified module. If this flag is not passed, the default module isansible.builtin.command
so you can pass a command with ‘-a’ flag-a, --args
module options
# authentication with password
ansible all -i x_IP_address, -k -m ping
# authentication with password, remote user name specified
ansible all -i web_servers.yml -u x_remote_user_name -k -a '/sbin/reboot'
# authentication with private key, remote user name specified
ansible all -i x_IP_address, \
-K -u x_remote_user_name --private-key '<x_path_to_private_key>' \
-m ansible.builtin.service -a 'name=httpd state=started'
# authentication with private key, user name and private key file name from `~/.ssh/config`
ansible all -i inventories/development/web_servers.yml -m ping
Playbooks
# authentication with password
ansible-playbook -i x_IP_address, -k test_playbook.yml
# authentication with password, remote user name specified
ansible-playbook -i x_IP_address, -u x_remote_user_name -k test_playbook.yml
# authentication with private key, remote user name specified
# also specify become user (joker) and asks become password
ansible-playbook -i x_IP_address, -u x_remote_user \
--private-key '<x_path_to_private_key>' \
--become-user joker --ask-become-pass test_playbook.yml
# authentication with private key, user name and private key file name from `~/.ssh/config`
# execute the playbook for all the hosts defined in 'inventories/development/web_servers.yml'
ansible-playbook -i inventories/development/web_servers.yml test_playbook.yml
# execute the playbook for 'web_server_2' defined in 'inventories/test/web_servers.yml'
ansible-playbook -i inventories/test/web_servers.yml --limit web_server_2 test_playbook.yml
Variables
There are a few ways to pass variables to playbooks, see Where to set variables for extended information.
Generally the variables are set in inventory files, there are some in the provided example configuration.
The -e
or --extra-vars
flags are used to pass variables in the command line.
For the full reference see Defining variables at runtime.
Here are some examples adapted form that documentation:
# The key=value format works for strings
ansible-playbook release.yml --extra-vars "version=1.23.45 other_variable=foo"
# JSON format is needed to pass non-string values such as Booleans, integers,
# floats, lists, and so on. You must escape quotes and other special characters
# appropriately for both your markup (for example, JSON), and for your shell
ansible-playbook release.yml --extra-vars \
'{"version":"1.23.45","other_variable":"foo","ghosts":["inky","pinky","sue"]}'
If you put the variables in a JSON or YAML file, no shell escaping is needed. Pass the file with variables like:
ansible-playbook release.yml --extra-vars "@some_file.json"
Final words
Again, do yourself a favor and:
- add the identity of your remote hosts to
~/.ssh/config
. See SSH Config File for information - add the remote hosts to an inventory file
- load private keys in
ssh-agent
while running Ansible commands - read at least the Getting started with Ansible article.