Just a quick write-up some stuff I was doing with Ansible today.
This is all on a Fedora 23 machine.
Using an ssh key makes all of this easier:
ssh-keygen -t rsa
Then:
ssh-copy-id -i <ip address of remote server>
Download ansible:
sudo dnf -y install ansible
First thing I did was make a new hosts file to clean it up.
sudo mv /etc/ansible/hosts /etc/ansible/hosts.old
Then make another one:
sudo touch /etc/ansible/hosts
The hosts folder holds all of your host names and ip addresses. Make a couple groups for your servers:
[webservers]
jhbcomputers.com
webserver.com
[local]
10.1.10.2
10.1.10.5
There are a couple options I've used in my hosts file, and may be helpful. My website is behind cloudflare, so if I ssh to the domain name it doesn't do anything. You can set a host name and ssh port like this:
[webservers]
xxx.xxx.xxx.xxx ansible_ssh_port=<custom port> ansible_host=<domain>
Once the hosts file is set up we can start running commands.
ansible webservers -m ping
returns:
server2 | success >> {
"changed": false,
"ping": "pong"
}
server2 | success >> {
"changed": false,
"ping": "pong"
}
Another example would be getting uptime from all of your servers:
ansible webservers -m command -a 'uptime'
server1 | success | rc=0 >>
01:34:21 up 5:17, 1 user, load average: 0.00, 0.02, 0.05
server2 | success | rc=0 >>
01:34:23 up 5:15, 1 user, load average: 0.00, 0.01, 0.05
The -m argument tells Ansible which module to use, and the -a argument tells it what arguments to pass to the module.
You could run everything from ad hoc commands like this, but that could get old.
Here's an example playbook I created to update a couple webservers:
---
- hosts: webservers
gather_facts: yes
remote_user: john
tasks:
- name: Backup Drupal
shell: chdir=/var/www/html/{{ansible_host}} drush archive-dump
- name: Update
yum: name=*
state=latest
update_cache=yes
become: yes
become_method: sudo
The playbook is stored in a .yml file. These always start with three --- at the top.
There are a couple things going on here. First the playbook sees we are running this on the webservers group in our hosts file.
Gather Facts will grab a ton of info about the server and store it in variables. It will store things like the Linux distro, user directory, user id, user gid, disks, amount of free space, ssh key, and a ton more.
Remote_user is the user that you are running the commands with on the remote system.
The tasks section holds the tasks to be completed. Mine is really simple, it just has a couple tasks. You can run things called handlers which will run when a task is completed, but I didn't need them for this.
The first task that runs is named Backup Drupal. It runs these commands:
cd /var/www/html/<sitename>
and then does
drush archive-dump
Each website is stored in a folder that is the domain name. So {{ ansible_host }} grabs the host name from the hosts file (this is the ansible_host=<name> part) and places it in the command. Drush is a utility for Drupal that lets you run a ton of stuff from the cli. So archive-dump creates a backup of the web folder and does a mysql dump of the database and saves it in the home folder of the user who ran the command. This way if something happens after the system update in the second task, I can just run drush archive-restore and it will pull everything back in.
The next task that runs is the system update task. It uses the yum module and updates (state=latest) all packages (name=*). I don't know if I need the update_cache=yes but it was in someone else's write up so I used it. I may not because here's the ansible doc on it:
"Run the equivalent of apt-get update before the operation. Can be run as part of the package installation or as a separate step."
The last two lines tell the task that you want to run as sudo. It will ask you for the sudo password after you run the playbook.
To run this playbook you would type:
ansible-playbook <name-of-playbook>.yml