Lesson 5 of 11 ↓
- 1.Ansible Basic Setup Guide
- 2.Ansible Inventory Guide (hosts)
- 3.Ansible Configuration Guide (ansible.cfg)
- 4.Ansible Ad-hoc Commands Guide
- 5.Ansible Playbook Guide (playbook.yml)
- 6.Ansible Variables & Precedence Guide
- 7.Ansible Loops Guide
- 8.Ansible Conditionals Guide (when)
- 9.Ansible Vault Guide
- 10.Ansible Handlers Guide
- 11.Ansible Custom Roles Guide
11 min read
Ansible Playbook Guide (playbook.yml)
This document provides a comprehensive and detailed explanation of Ansible Playbooks. It breaks down the syntax, logic, execution methods, and every single module used, designed to be a reference for beginners and pros alike.
Section 1: Introduction & Anatomy
Why Use Ansible? (the Benefits)
Based on core principles, here is why Ansible is powerful:
-
✅ Agentless: No daemons or agents installed on nodes (uses SSH).
-
✅ Simple: Easy to learn with YAML syntax.
-
✅ Powerful: Handles complex deployments and orchestrations.
-
✅ Repeatable: Ensures consistent environments.
-
✅ Idempotent: Tasks run only when needed (no changes if state is correct).
-
✅ Extensible: Use custom modules, plugins, and roles.
What is a Playbook?
An Ansible Playbook is a YAML file that describes a set of automation steps. Think of it as a "ToDo List" for your servers.
Basic Structure Rules
-
Starts with
---: This indicates the start of a YAML file. -
Hyphens (
-): Indicate a list item (e.g., a Play or a Task). -
Indentation: Critical in YAML. Use 2 spaces for indentation. Never use tabs.
The "play" Hierarchy
A Playbook contains one or more Plays.
-
Play: Maps a group of hosts to a list of tasks.
-
Hosts: Who are we automating? (e.g.,
web,db,localhost). -
Become: Do we need root? (sudo).
-
Tasks: What are we doing? (The actual steps).
-
Section 2: Local Automation Example (understanding Syntax)
This play runs locally on your machine, not on a remote server. It's great for testing.
---
- name: Play 1 - Local Automation
hosts: localhost
connection: local
tasks:
- name: Execute command 'date'
command: date
- name: Execute script on server
script: test_script.sh
- name: Play 2 - Web Service Setup
hosts: localhost
become: true
tasks:
- name: Install web service
yum:
name: httpd
state: present
- name: Start web server
service:
name: httpd
state: startedDeep Dive Into Part 1
-
hosts: localhost: Tells Ansible to run this play on the machine you are currently typing on (the Control Node). -
connection: local: Optimizes the connection. Since it's the same machine, Ansible doesn't need to open an SSH tunnel. -
become: true:-
This is equivalent to typing
sudobefore a command. -
Required for
yum(installing packages) andservice(starting daemons).
-
-
commandModule:-
Runs a raw Linux command.
-
Note: It is not idempotent. If you run
mkdir folder, it works once. If you run it again, it fails (folder exists). Use thefilemodule for folders instead.
-
-
scriptModule:- Takes a script from your local machine (Control Node), copies it to the remote node, runs it, and then deletes it.
Section 3: the Logic of "cleanup" (decommissioning)
This example teaches you how to logically remove software. You can't just delete files; you must stop the process first.
- name: Remove NGINX from Amazon Linux EC2
hosts: all
become: true
tasks:
# 1. Stop the service first. We can't delete running programs safely.
- name: Stop nginx service if running
service:
name: nginx
state: stopped
ignore_errors: true
# 2. Disable it so it doesn't try to start on reboot (ghost service).
- name: Disable nginx service
service:
name: nginx
enabled: no
ignore_errors: true
# 3. Now it's safe to uninstall the binary package.
- name: Remove nginx package
yum:
name: nginx
state: absent
# 4. Clean up configuration files (yum often leaves these behind).
- name: Delete nginx configuration directory
file:
path: /etc/nginx
state: absent
# 5. Clean up data/website files.
- name: Delete default nginx HTML directory
file:
path: /usr/share/nginx
state: absentDeep Dive Into Cleanup Logic
-
state: stopped: Stops the process immediately. -
enabled: no: Removes the symbolic link from systemd (systemctl disable). -
ignore_errors: true:-
Why? If Nginx is already uninstalled, the
servicemodule would normally fail saying "Service not found". -
This flag tells Ansible: "Try to stop it, but if you fail (because it's not there), just keep going to the next task." This makes the playbook Robust.
-
-
state: absent: The universal keyword for removal.-
For
yum: Uninstalls the package. -
For
file: Recursively deletes directories (likerm -rf). -
For
user: Deletes the user account.
-
Section 4: Common Tasks Library
This section explains the most used modules in real-world DevOps scenarios.
Web & Services
1. Install Apache (httpd)
- name: Install Apache Web Server
hosts: all
become: true
tasks:
- name: Install httpd
yum:
name: httpd
state: present # Ensures it is installed. Use 'latest' to update.
- name: Start httpd service
service:
name: httpd
state: started # Starts the service now.
enabled: true # Ensures it starts automatically after reboot.**2. Restart Ssh Service (handler Pattern)
- name: Restart SSH service
hosts: all
become: true
tasks:
- name: Restart sshd
service:
name: sshd
state: restarted # Stops and Start the service.- Use Case: You typically run this after modifying
/etc/ssh/sshd_config.
**3. Configure Firewall (firewalld)
- name: Open port 80 in firewalld
hosts: all
become: true
tasks:
- name: Allow HTTP traffic
firewalld:
port: 80/tcp
permanent: true # Writes rule to disk (survives reboot).
state: enabled
immediate: yes # Applies rule NOW (no reload needed).- Note: Without
immediate: yes, the rule would only apply after a firewall reload or reboot.
**4. Start and Enable a Service (general)
- name: Start and enable firewalld
hosts: all
become: true
tasks:
- name: Start firewalld
service:
name: firewalld
state: started
enabled: trueUser & Access Management
**5. Create a User
- name: Create a user called devops
hosts: all
become: true
tasks:
- name: Add user devops
user:
name: devops
state: present
groups: wheel # Adds user to 'wheel' group (sudoers).
append: yes # CRITICAL: If 'no', it removes user from all other groups!**6. Delete a User (deep Clean)
- name: Remove user 'testuser'
hosts: all
become: true
tasks:
- name: Delete testuser
user:
name: testuser
state: absent
remove: yes # CRITICAL: Deletes /home/testuser and mail spool.- Why
remove: yes? By default, Linux deletes the user account but keeps their files in/home. This flag ensures a clean wipe.
**7. Set Hostname
- name: Set system hostname
hosts: all
become: true
tasks:
- name: Change hostname to "web01"
hostname:
name: web01File & Directory Management
**8. Copy a File (push)
- name: Copy index.html to web server
hosts: all
become: true
tasks:
- name: Copy file
copy:
src: ./index.html # Source file on YOUR machine.
dest: /var/www/html/index.html # Destination on REMOTE server.**9. Create a Directory
- name: Create directory on remote host
hosts: all
become: true
tasks:
- name: Make /opt/demo
file:
path: /opt/demo
state: directory # Tells Ansible this is a folder, not a file.
mode: '0755' # rwxr-xr-x permissions.**10. Set File Permissions & Ownership
- name: Set permissions on a config file
hosts: all
become: true
tasks:
- name: Set mode and ownership
file:
path: /etc/myconfig.conf
mode: '0644'
owner: root
group: root
state: file**11. Remove a Directory
- name: Remove temporary directory
hosts: all
become: true
tasks:
- name: Delete /tmp/old_data
file:
path: /tmp/old_data
state: absent # Recursively deletes directory and contents.**12. Modify File Content (idempotent Edit)
- name: Add banner to /etc/motd
hosts: all
become: true
tasks:
- name: Add welcome message
lineinfile:
path: /etc/motd
line: "Welcome to your server - managed by Ansible"- Magic:
lineinfilechecks if the line exists first. If it does, it does nothing (Idempotent). If not, it adds it.
**13. Create an Empty File (touch)
- name: Create a log file
hosts: all
become: true
tasks:
- name: Touch /var/log/app.log
file:
path: /var/log/app.log
state: touch # Like the Linux 'touch' command.
mode: '0644'System Configuration
**14. Install Epel Repository
- name: Install EPEL repository
hosts: all
become: true
tasks:
- name: Install epel-release
yum:
name: epel-release
state: present- Why? Amazon Linux and CentOS often need "Extra Packages for Enterprise Linux" (EPEL) to install common tools like Nginx or htop.
**15. Mount a Volume
- name: Mount a filesystem
hosts: all
become: true
tasks:
- name: Mount /dev/xvdf1 on /mnt/data
mount:
path: /mnt/data # Where to mount.
src: /dev/xvdf1 # The device/disk.
fstype: ext4
state: mounted # Mounts NOW + Adds to /etc/fstab (Persist).**16. Set System Timezone
- name: Set timezone to UTC
hosts: all
become: true
tasks:
- name: Configure timezone
timezone:
name: UTC- Why? Servers should always be in UTC to avoid log confusion across timezones.
**17. Add Dns Resolver
- name: Add DNS server to resolv.conf
hosts: all
become: true
tasks:
- name: Add Google DNS
lineinfile:
path: /etc/resolv.conf
line: "nameserver 8.8.8.8"**18. Create a Swap File
This task involves multiple steps using command and file.
- name: Create 1GB swap file
hosts: all
become: true
tasks:
- name: Create swap file
command: dd if=/dev/zero of=/swapfile bs=1M count=1024
args:
creates: /swapfile # Crucial: Only runs if /swapfile doesn't exist
- name: Set permissions
file:
path: /swapfile
mode: '0600'
- name: Make it swap
command: mkswap /swapfile
when: ansible_facts['swapfree_mb'] == 0 # Conditional execution
- name: Enable swap
command: swapon /swapfile
when: ansible_facts['swapfree_mb'] == 0**19. Reboot the Server
- name: Reboot server after changes
hosts: all
become: true
tasks:
- name: Reboot the machine
reboot:
reboot_timeout: 300 # Wait 5 minutes max for it to come back.- Magic: Ansible disconnects, waits for the server to restart, reconnects, and then continues the playbook.
Section 5: Advanced Execution Options
This section covers critical options for running playbooks efficiently and safely.
Verification & Dry Runs
- Syntax Check: Checks for YAML errors without running.
ansible-playbook playbook.yml --syntax-check- Dry Run / Check Mode: Simulates execution.
ansible-playbook playbook.yml -CDebugging & Verbosity
-
-v: Show task results. -
-vvv: Show connection info (good for verifying SSH).
Controlling Execution Scope
- Limit: Run only on specific hosts/groups.
ansible-playbook playbook.yml --limit db- Forks: Control parallelism (default is 5).
ansible-playbook playbook.yml --forks 20Section 6: Managing Multiple Playbooks & Workflows
As your infrastructure grows, putting everything in one file becomes messy. Here are the methods to manage complex workflows.
Method 1: Multi-play in One Yaml File
You can define multiple plays in a single file (multi_playbook.yml), each targeting different groups.
# Play 1: Target Web Servers
- name: Install Apache on web servers
hosts: web
become: true
tasks:
- name: Install httpd
yum:
name: httpd
state: present
# Play 2: Target DB Servers
- name: Install MariaDB on db servers
hosts: db
become: true
tasks:
- name: Install MariaDB
yum:
name: mariadb-server
state: presentMethod 2: the Master Playbook (import_playbook)
Use this to statically include other playbooks. It acts as a "Parent" playbook that calls "Child" playbooks.
File: site.yml
---
- import_playbook: web.yml
- import_playbook: db.ymlExecution:
ansible-playbook site.ymlMethod 3: Dynamic Task Inclusion (include_tasks)
Use this inside a task list to organize large plays.
File: main.yml
- name: Common Setup
hosts: all
become: true
tasks:
- name: Include web tasks
include_tasks: web-tasks.yml
- name: Include db tasks
include_tasks: db-tasks.ymlFile: web-tasks.yml
- name: Install nginx
yum:
name: nginx
state: presentFile: db-tasks.yml
- name: Install mariadb
yum:
name: mariadb-server
state: presentMethod 4: Using Tags for Selectivity
Tags allow you to run specific parts of a large playbook without running everything.
File: site.yml
- name: Web tasks
hosts: web
become: true
tasks:
- name: Install nginx
yum:
name: nginx
state: present
tags: web # <--- Assigned Tag
- name: DB tasks
hosts: db
become: true
tasks:
- name: Install mariadb
yum:
name: mariadb-server
state: present
tags: db # <--- Assigned TagExecution: Run ONLY the web parts:
ansible-playbook site.yml --tags webMethod 5: Shell Scripts & Chaining
You can create a simple bash script to run multiple playbooks sequentially, or use one-liners.
Shell Script (run.sh):
#!/bin/bash
ansible-playbook web.yml
ansible-playbook db.yml
ansible-playbook firewall.ymlOne-Liner:
ansible-playbook web.yml && ansible-playbook db.ymlModule Quick Reference Table
| Module | Use Case | Key Arguments |
|---|---|---|
yum |
Installing/Removing software | name, state=present/absent |
service |
Starting/Stopping daemons | name, state=started/stopped, enabled=yes |
file |
Files/Folders permissions | path, state=directory/touch/absent, mode |
copy |
Uploading files | src (local), dest (remote) |
user |
Managing Users | name, groups, remove=yes |
lineinfile |
Editing config files | path, line, regexp |
shell |
Complex commands | Used when command module is too limited (pipes/redirects) |
Comments
Loading the discussion…