Difference between revisions of "Ansible"

From Indie IT Wiki
(16 intermediate revisions by the same user not shown)
Line 9: Line 9:
  
 
[https://www.digitalocean.com/community/tutorials/how-to-install-and-configure-ansible-on-ubuntu-20-04.amp How To Install and Configure Ansible on Ubuntu 20.04]
 
[https://www.digitalocean.com/community/tutorials/how-to-install-and-configure-ansible-on-ubuntu-20-04.amp How To Install and Configure Ansible on Ubuntu 20.04]
 +
 +
== Requirements ==
 +
 +
Python 2.6+ or Python 3.5+
  
 
== Installation ==
 
== Installation ==
Line 38: Line 42:
 
           ansible_python_interpreter: /usr/bin/python3
 
           ansible_python_interpreter: /usr/bin/python3
 
     ungrouped: {}
 
     ungrouped: {}
 +
 +
Check the config with hosts file specified...
 +
 +
<code>ansible-inventory --list -y -i ./inventory/hosts</code>
  
 
== Testing ==
 
== Testing ==
 +
 +
=== List Hosts ===
 +
 +
<code>./inventory/hosts</code>
 +
 +
[servers]
 +
server1 ansible_connection=ssh ansible_user=username1
 +
domain.uk ansible_connection=ssh ansible_user=username2
 +
nas ansible_connection=ssh ansible_user=username3
 +
 +
ansible -i ./inventory/hosts servers --list-hosts
 +
 +
  hosts (3):
 +
    server1
 +
    domain.uk
 +
    nas
 +
 +
=== Ping ===
 +
 +
ansible -i ./inventory/hosts servers -m ping
 +
ansible -i ./inventory/hosts server1.mydomain.com -m ping
 +
 +
=== Echo ===
 +
 +
Get all hosts to output a word on the command line...
 +
 +
ansible all -a "/bin/echo hello" -i ./inventory/hosts
 +
 +
=== Uptime ===
 +
 +
Uptime for a single host...
 +
 +
ansible hostname -m command -a "uptime" -i ./inventory/hosts
 +
 +
Uptime for all hosts in a group...
 +
 +
ansible groupname -m command -a "uptime" -i ./inventory/hosts
 +
 +
Uptime for all hosts...
 +
 +
ansible all -m command -a "uptime" -i ./inventory/hosts
  
 
=== AWS SSH Key ===
 
=== AWS SSH Key ===
Line 69: Line 118:
  
 
=== Examples ===
 
=== Examples ===
 +
 +
'''See if hosts are alive by using only Gather Facts'''
 +
 +
<code>99_gather.yml</code>
 +
 +
- name: gather facts
 +
  become: true
 +
  hosts: all
 +
 +
... and run it on all but 1 host (by using the limit option with an exclamation mark ('''!host''') ('''!host1:!host2''')...
 +
 +
ansible-playbook -i ~/Bin/ansible-homelab/inventory/hosts ~/Bin/ansible-homelab/playbooks/ubuntu/99_gather.yml --limit '!server1'
  
 
'''Update Package List and Upgrade System'''
 
'''Update Package List and Upgrade System'''
Line 77: Line 138:
  
 
  [servers]
 
  [servers]
  servername ansible_connection=ssh ansible_user=username
+
  server1 ansible_connection=ssh ansible_user=user1
 +
server2 ansible_connection=ssh ansible_user=user2
 +
server3 ansible_connection=ssh ansible_user=user3
 +
 
 +
Check the list of hosts is readable..
 +
 
 +
ansible -i ./inventory/hosts all --list-hosts
  
 
Create the playbook file...
 
Create the playbook file...
Line 95: Line 162:
 
  ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts
 
  ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts
  
'''Create single directory using the 'file' module.'''
+
To run this playbook on a single host or multiple hosts, you would use the -l (limit) option at the end of the command line...
 +
 
 +
ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts -l server1
 +
ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts -l server1,server2
 +
 
 +
'''Create single directory using the 'file' module'''
  
 
Create the playbook...
 
Create the playbook...
Line 116: Line 188:
 
<code>ansible-playbook mkdir.yml</code>
 
<code>ansible-playbook mkdir.yml</code>
  
'''Create multiple directories using the 'file' module.'''
+
'''Create multiple directories using the 'file' module'''
  
 
Create the playbook...
 
Create the playbook...
Line 139: Line 211:
 
https://linuxhint.com/create-directory-ansible/
 
https://linuxhint.com/create-directory-ansible/
  
'''Install Apache web server software and start it on a Red Hat based system...'''
+
'''Install Apache web server software and start it on a Red Hat based system'''
  
 
  - name: Playbook
 
  - name: Playbook
Line 154: Line 226:
 
         name: httpd
 
         name: httpd
 
         state: started
 
         state: started
 +
 +
'''Touch a file based on the date of another file'''
 +
 +
- hosts: alpine
 +
  become: yes
 +
  tasks:
 +
  - name: Get stats of a file
 +
    ansible.builtin.stat:
 +
      path: /usr
 +
    register: usr
 +
  - name: Print a debug message
 +
    ansible.builtin.debug:
 +
      msg: "Path exists and is a directory"
 +
    when: usr.stat.isdir is defined and usr.stat.isdir
 +
  - name: Print a debug message
 +
    ansible.builtin.debug:
 +
      msg: "ctime is <nowiki>{{ usr.stat.ctime }}</nowiki>"
 +
  - name: touch file /root/misc/system_installed
 +
    file:
 +
      path: /root/misc/system_installed
 +
      state: touch
 +
      modification_time: '<nowiki>{{ "%Y%m%d%H%M.%S" | strftime(usr.stat.ctime) }}</nowiki>'
 +
 +
== Variables ==
 +
 +
{{ ansible_facts["eth0"]["ipv4"]["address"] }}
 +
 +
https://docs.ansible.com/ansible/latest/user_guide/playbooks_variables.html

Revision as of 09:42, 2 December 2021

Introduction

Ansible is an open-source software provisioning, configuration management, and application-deployment tool enabling infrastructure as code.

It is used to deploy and maintain many servers at once, from the command line.

  • Control Node = Admin Computer
  • Host Node = Remote Server

How To Install and Configure Ansible on Ubuntu 20.04

Requirements

Python 2.6+ or Python 3.5+

Installation

sudo apt-get -y install ansible

Configuration

Add your hosts...

sudo nano /etc/ansible/hosts

[servers]
myserver ansible_host=123.456.789.0

[all:vars]
ansible_python_interpreter=/usr/bin/python3

Check the config...

ansible-inventory --list -y

all:
  children:
    servers:
      hosts:
        myserver:
          ansible_host: 123.456.789.0
          ansible_python_interpreter: /usr/bin/python3
    ungrouped: {}

Check the config with hosts file specified...

ansible-inventory --list -y -i ./inventory/hosts

Testing

List Hosts

./inventory/hosts

[servers]
server1 ansible_connection=ssh ansible_user=username1
domain.uk ansible_connection=ssh ansible_user=username2
nas ansible_connection=ssh ansible_user=username3
ansible -i ./inventory/hosts servers --list-hosts

 hosts (3):
   server1
   domain.uk
   nas

Ping

ansible -i ./inventory/hosts servers -m ping
ansible -i ./inventory/hosts server1.mydomain.com -m ping

Echo

Get all hosts to output a word on the command line...

ansible all -a "/bin/echo hello" -i ./inventory/hosts

Uptime

Uptime for a single host...

ansible hostname -m command -a "uptime" -i ./inventory/hosts

Uptime for all hosts in a group...

ansible groupname -m command -a "uptime" -i ./inventory/hosts

Uptime for all hosts...

ansible all -m command -a "uptime" -i ./inventory/hosts

AWS SSH Key

ansible all -m ping -u ubuntu --private-key=~/.ssh/myserver.pem

myserver | SUCCESS => {
   "changed": false,
   "ping": "pong"
}

Commands

You can perform one off commands on a single host or multiple hosts.

Hostname

ansible all -u ubuntu --private-key=~/.ssh/myserver.pem -a "hostname -f"

Update Package Cache

ansible all -u ubuntu --private-key=~/.ssh/myserver.pem -a "sudo apt-get update"

Playbooks

Playbooks are YAML text files which contain commands and options in a text file, just like a docker compose file.

The file contains 'modules' which perform different tasks.

Examples

See if hosts are alive by using only Gather Facts

99_gather.yml

- name: gather facts
  become: true
  hosts: all

... and run it on all but 1 host (by using the limit option with an exclamation mark (!host) (!host1:!host2)...

ansible-playbook -i ~/Bin/ansible-homelab/inventory/hosts ~/Bin/ansible-homelab/playbooks/ubuntu/99_gather.yml --limit '!server1'

Update Package List and Upgrade System

Create hosts file...

./inventory/hosts

[servers]
server1 ansible_connection=ssh ansible_user=user1
server2 ansible_connection=ssh ansible_user=user2
server3 ansible_connection=ssh ansible_user=user3

Check the list of hosts is readable..

ansible -i ./inventory/hosts all --list-hosts

Create the playbook file...

./playbooks/apt.yml

- hosts: "*"
  become: yes
  tasks:
    - name: apt
      apt:
        update_cache: yes
        upgrade: 'yes'

Run the playbook command...

ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts

To run this playbook on a single host or multiple hosts, you would use the -l (limit) option at the end of the command line...

ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts -l server1
ansible-playbook ./playbooks/apt.yml -i ./inventory/hosts -l server1,server2

Create single directory using the 'file' module

Create the playbook...

nano mkdir.yml

- hosts: all
  tasks:
  - name: Ansible file module create directory
    file:
      path: ~/backups
      state: directory

Run the playbook (dry run)...

ansible-playbook -C mkdir.yml

Run the playbook...

ansible-playbook mkdir.yml

Create multiple directories using the 'file' module

Create the playbook...

nano mkdirs.yml

- hosts: all
  tasks:
  - name: Ansible create multiple directories with_items    
    file:
      path: ~/backups/{{item}}
      state: directory
      with_items:
      - 'mysql'      
      - 'repository'
      - 'config'

Run the playbook...

ansible-playbook mkdirs.yml

https://linuxhint.com/create-directory-ansible/

Install Apache web server software and start it on a Red Hat based system

- name: Playbook
  hosts: webservers
  become: yes
  become_user: root
  tasks:
    - name: ensure apache is at the latest version
      yum:
        name: httpd
        state: latest
    - name: ensure apache is running
      service:
        name: httpd
        state: started

Touch a file based on the date of another file

- hosts: alpine
  become: yes
  tasks:
  - name: Get stats of a file
    ansible.builtin.stat:
      path: /usr
    register: usr
  - name: Print a debug message
    ansible.builtin.debug:
      msg: "Path exists and is a directory"
    when: usr.stat.isdir is defined and usr.stat.isdir
  - name: Print a debug message
    ansible.builtin.debug:
      msg: "ctime is {{ usr.stat.ctime }}"
  - name: touch file /root/misc/system_installed
    file:
      path: /root/misc/system_installed
      state: touch
      modification_time: '{{ "%Y%m%d%H%M.%S" | strftime(usr.stat.ctime) }}'

Variables

{{ ansible_facts["eth0"]["ipv4"]["address"] }}

https://docs.ansible.com/ansible/latest/user_guide/playbooks_variables.html