Ansible
Ansible (an IT automation, Configuration Management and Provision tool) is a simple, flexible, and
extremely powerful tool that gives you the ability to automate common infrastructure tasks, run ad
hoc commands, and deploy multitier applications spanning multiple machines.
Main features
● Age tless ● Se u e ● P o isio i g AND deplo e t ● Eas to sta t ● Ide pote t
Controller: This is the only host that needs to have Ansible installed, and works as a controller. This
is used to launch the ansible-playbook commands from the controller.
Ansible is agentless and manages nodes using SSH transport, no additional setup is needed on the
nodes except for ensuring that the SSH service is running.
KEY COMPONENTS
★ Modules (Tools) ★ Tasks ★ Inventory ★ Plays ★ Playbook (Plan)
A playbook consists of one or more plays, which map groups of hosts to well-defined tasks.
YAML – the playbook language:
• The fi st li e of a pla ook should egi ith "--- " (three hyphens) which indicates the beginning
of the YAML document.
• Lists i YAML a e ep ese ted ith a h phe follo ed a white space. A playbook contains a list
of plays; they are represented with "- ". Each play is an associative array, a dictionary, or a map in
terms of key-value pairs.
• I de tatio s a e i po ta t. All e e s of a list should e at the sa e i de tatio le el. • Ea h
play can contain key-value pairs separated by ":" to denote hosts, variables, roles, tasks, and so on.
Creating a host inventory:
Before we even start writing our playbook with Ansible, we need to define an inventory of all hosts
that need to be configured, and make it available for Ansible to use. Later, we will start running plays
against a selection of hosts from this inventory. For text-based local inventory, the default location is
/etc/ansible/hosts.
Tasks:
Plays map hosts to tasks. Tasks are a sequence of actions performed against a group of hosts that
match the pattern specified in a play. Each play typically contains multiple tasks that are run serially
on each machine that matches the pattern.
Modules:
Modules are the encapsulated procedures that are responsible for managing specific system
o po e ts o spe ifi platfo s. Co side the follo i g e a ple: • The apt odule fo De ia a d
the u odule fo RedHat helps a age s ste pa kages • The use odule is responsible for
addi g, e o i g, o odif i g use s o the s ste • The se i e odule ill sta t/stop s ste
services Modules abstract the actual implementation from users. They expose a declarative syntax
that accepts a list of the parameters and states of the system components being managed. All this
can be declared using the human-readable YAML syntax, using key-value pairs.
Bits of code copied to the target system. Executed to satisfy the task declaration.
LIST ALL MODULES
#ansible-doc -l
VIEW MODULE DOCUMENTATION
#ansible-doc <module_name>
The modules and idempotence:
Idempotence is an important characteristic of a module. It is something which can be applied on
your system multiple times, and will return deterministic results. It has built-in intelligence. For
instance, we have a task that uses the apt module to install Nginx and ensure that it's up to date.
Here is what happens if you run it multiple times:
• E e ti e ide pota e is u ultiple ti es, the apt odule ill o pa e hat has been
declared in the playbook versus the current state of that package on the system. The first time it
runs, Ansible will determine that Nginx is not installed, and will go ahead with the installation.
• Fo e e o se ue t u , it ill skip the installation part, unless there is a new version of the
package available in the upstream repositories. This allows executing the same task multiple times
without resulting in the error state. Most of the Ansible modules are idempotent, except for the
command and shell modules. Users will have to make these modules idempotent.
Understanding roles:
Roles provide a way to create modular code, which then can then be shared and reused.
Lab setup:
server1:
# iptables -F
#service iptables stop
# chkconfig iptables
# vi /etc/sysconfig/selinux
SELINUX=disabled
# vi /etc/hosts
IPaddr1 server1
IPaddr2 server2
IPaddr3 server3
#userdd test
# passwd test
# visudo
test ALL=(ALL) NOPASSWD:ALL
# reboot
Perform above steps on server2 and server3.
server1:
# yum install epel-release
# yum install ansible
# cd /etc/ansible
#mv hosts [Link]
#vi hosts
[webserver]
server2
server3
# su – test
$ ssh-keygen
$ ssh-copy-id server2
$ ssh-copy-id server3
Discuss about ad-hoc commands in class.
All the below example run as test user.
Example1:
$ vi [Link]
--- # webserver setup
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package
yum: name=httpd state=present
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name=httpd state=started
$ ansible-playbook [Link]
Example2:
$ vi [Link]
--- # Learning about variables
- hosts: '{{host}}'
remote_user: test
become: yes
vars:
pkg1: httpd
vars_files:
- [Link]
vars_prompt:
- name: pkg3
prompt: enter package name
private: no
tasks:
- name: installing httpd package
yum: name={{pkg1}} state=present
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name={{pkg1}} state=started
- name: installing telnet package
yum: name={{pkg2}} state=present
- name: installing user given package
yum: name={{pkg3}} state=present
$ more [Link]
---
pkg2: telnet
$ ansible-playbook [Link] –extra-vars hosts=webserver
Example3:
Dealing with errors.
$ vi [Link]
--- # errors programs
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package
yum: name=httpd1 state=present
ignore_errors: yes
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name=httpd state=started
$ ansible-playbook [Link]
Example4:
Handler usage:
● Spe ial task, u s o l if the e as ha ge.
● Usa le fo se i e esta ts, data ase upload, ...
$ vi [Link]
--- # handler usage
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package
yum: name=httpd state=present
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
notify: start httpd service
handlers:
- name: start httpd service
service: name=httpd state=restarted
$ ansible-playbook [Link]
Example5:
Command,Shell, Raw amd Script modules.
$ vi [Link]
--- # commands example
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: create a file
command: touch testfile creates=/home/user1/testfile
- name: list of all files
shell: ls > /tmp/abc
- name: create directory
raw: mkdir /home/user1/testdir3 creates=/home/user1/ppp
- name: execute a script
script: ./[Link]
$ more [Link]
#! /bin/bash
echo "hello" > /home/user1/file1
$ ansible-playbook [Link]
Example6:
Gathering facts
$ vi [Link]
--- # gather facts
- hosts: webserver
remote_user: test
become: yes
gather_facts: yes
tasks:
- name: installing httpd package
yum: name=httpd state=present
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name=httpd state=started
$ ansible-playbook [Link]
Example7:
$ vi [Link]
--- # example on condition
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package on Redhat
yum: name=httpd state=present
when: ansible_os_family == "RedHat"
- name: installing httpd package on ubuntu
yum: name=apache2 state=present
when: ansible_os_family == "Debian"
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name=httpd state=started
$ ansible-playbook [Link]
Example8:
$ vi [Link]
--- # template example
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: copy new [Link]
template: src=[Link].j2 dest=/tmp/[Link]
$ more [Link].j2
hello
{{ansible_hostname}}
World
$ ansible-playbook [Link]
Example 9:
$ vi [Link]
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package
yum: name=httpd state=present
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
- name: start httpd server
service: name=httpd state=started
register: result
- debug: var=result
$ ansible-playbook [Link]
Example10:
$ vi [Link]
--- # tag example
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing httpd package
yum: name=httpd state=present
tags:
- install
- name: copy [Link]
copy: src=[Link] dest=/var/www/html
tags:
- copy
- name: start httpd server
service: name=httpd state=started
tags:
- service
$ ansible-playbook [Link] --tags install
Example11:
Loops:
$ vi [Link]
- hosts: webserver
remote_user: test
become: yes
tasks:
- name: installing packages
yum: name={{item}}httpd state=present
with_items:
- lynx
- telnet
- curl
$ ansible-playbook [Link]
Example12:
$ vi [Link]
--- # unarchive example
- hosts: server2
remote_user: test
become: yes
tasks:
- name: unarchiving to server 2 for test
unarchive: src=[Link] dest=/home/test
$ ansible-playbook [Link]
Example13:
$ vi [Link]
--- # get url setup
- hosts: server2
remote_user: test
become: yes
tasks:
- name: get url data
get_url: url=[Link] dest=/home/test/[Link]
$ ansible-playbook [Link]
Example14:
Roles
$ cd /home/test
$ mkdir roles
$ cd roles; mkdir webservers; cd webservers
$ mkdir {defaults,files,handlers,meta,tasks,templates,vars}
$ cd tasks
$ vi [Link]
---
- name: Install apache package
yum: pkg=httpd state=present
-name: copy [Link]
copy: src=[Link] dest=/var/www/html
notify: restart httpd
-name: start httpd service
service: name=httpd state=started
$ cd ../files
$ vi [Link]
Checking roles concept
$ cd ../handlers
$ vi [Link]
---
-name: restart httpd
Service: name=httpd state=restarted
$ vi [Link]
--- # role 1 Webserver setup
- hosts: webserver
remote_user: test
become_method: sudo
become: yes
roles:
- webservers
$ ansible-playbook [Link]
Example15:
Tomcat installation:
$ vi [Link]
--- # tomcat setup
- hosts: server2
remote_user: test
become: yes
tasks:
- name: remove older version of tomcat
file: path=/usr/local/tomcat state=absent
- name: download tomcat
get_url: url=[Link]
[Link] dest=/tmp
- name: create tomcat folder
command: mkdir /usr/local/tomcat
- name: extract archive
unarchive: src=/tmp/[Link] dest=/usr/local/tomcat copy=no
- name: create tomcat users
copy: src=/home/user1/[Link] dest=/usr/local/tomcat/apache-tomcat-7.0.78/conf/
- name: start tomcat
command: nohup /usr/local/tomcat/apache-tomcat-7.0.78/bin/[Link] &
$ ansible-playbook [Link]
Example16:
Ansible-vault can encrypt any structured data.
$ ansible-vault encrypt [Link]
$ ansible-playbook [Link] --ask-vault-pass
Example 17:
Using an Ansible playbook:
1. Change SELINUX to permissive mode on all your hosts
2. Install HTTPD on your web hosts only
3. Start and Enable HTTPD service on web hosts only if a new httpd package is installed.
4. Copy an motd file saying Welcome to my server! to all your hosts
5. Copy an hello world [Link] file to your web hosts in /var/www/html
6. Modify the [Link] to set PermitRootLogin at no
Solution:
$ vi [Link]
--
- hosts: all
remote_user: test
become: yes
vars:
selinux: permissive
tasks:
- name: Configure selinux to {{ selinux }}
selinux: policy: targeted state: "{{ selinux }}"
- name: Copy motd file
copy: src=motd dest=/etc/motd
-hosts: web
remote_user: test
become: yes
tasks:
- name: Install Apache
yum: name=httpd state=present
notify: Restart Apache
- name: Copy [Link]
copy: src=[Link] dest=/var/www/html/[Link]
- name: Set ssh root login at no
lineinfile: dest=/etc/ssh/sshd_config line="PermitRootLogin no" state=present
notify: RestartSSH
handlers:
- name: Restart Apache
service: name=httpd state=restarted enabled=yes
- name: RestartSSH
service: name=sshd state=restarted enable=yes
$ ansible-playbook [Link]
Discuss about Ansible Tower and Ansible Galaxy along with other cases in class.