Ansible Playbook Guide

Inventory

# inventory/hosts.ini [webservers] web1.example.com web2.example.com ansible_user=ubuntu [dbservers] db1.example.com ansible_host=10.0.1.10 ansible_port=2222 [production:children] webservers dbservers [production:vars] ansible_user=deploy ansible_ssh_private_key_file=~/.ssh/prod_key # inventory/hosts.yml (YAML format) all: children: webservers: hosts: web1.example.com: web2.example.com: ansible_user: ubuntu dbservers: hosts: db1.example.com: ansible_host: 10.0.1.10 # Run against inventory ansible -i inventory/hosts.ini webservers -m ping ansible-playbook -i inventory/hosts.ini deploy.yml

Playbook Structure

--- - name: Deploy web application hosts: webservers become: yes gather_facts: yes serial: 2 # rolling update: 2 at a time vars: app_version: "2.1.0" app_dir: /opt/myapp vars_files: - vars/common.yml - "vars/{{ansible_os_family}}.yml" pre_tasks: - name: Update apt cache apt: update_cache: yes cache_valid_time: 3600 when: ansible_os_family == "Debian" tasks: - name: Create app directory file: path: "{{app_dir}}" state: directory mode: '0755' owner: www-data - name: Deploy app copy: src: dist/ dest: "{{app_dir}}/" notify: Restart nginx handlers: - name: Restart nginx service: name: nginx state: restarted

Tasks & Modules

tasks: # Package management - name: Install packages package: name: "{{item}}" state: present loop: - nginx - git - python3-pip # Template file - name: Deploy nginx config template: src: templates/nginx.conf.j2 dest: /etc/nginx/nginx.conf validate: nginx -t -c %s notify: Reload nginx # Command with return value - name: Get current version command: /opt/myapp/bin/version register: current_version changed_when: false - debug: msg: "Running {{current_version.stdout}}" # Block with error handling - block: - name: Dangerous task command: /opt/upgrade.sh rescue: - name: Rollback on failure command: /opt/rollback.sh always: - name: Send notification debug: msg: "Upgrade attempt completed"

Variables & Conditionals

# Variable precedence (highest to lowest): # 1. extra vars (-e flag) # 2. task vars # 3. block vars # 4. role vars # 5. play vars_files # 6. host_vars / group_vars # 7. defaults # Conditionals - name: Install Apache on RHEL yum: name: httpd state: present when: - ansible_os_family == "RedHat" - ansible_distribution_major_version | int >= 8 - name: Deploy only if version changed copy: src: app.tar.gz dest: /opt/ when: current_version.stdout != app_version # Conditional import - import_tasks: tasks/centos.yml when: ansible_distribution == "CentOS" # Loops - name: Create users user: name: "{{item.name}}" groups: "{{item.groups}}" shell: /bin/bash loop: - { name: alice, groups: sudo } - { name: bob, groups: developers }

Roles Structure

roles/ โ””โ”€โ”€ nginx/ โ”œโ”€โ”€ tasks/ โ”‚ โ”œโ”€โ”€ main.yml โ”‚ โ”œโ”€โ”€ install.yml โ”‚ โ””โ”€โ”€ configure.yml โ”œโ”€โ”€ handlers/ โ”‚ โ””โ”€โ”€ main.yml โ”œโ”€โ”€ templates/ โ”‚ โ””โ”€โ”€ nginx.conf.j2 โ”œโ”€โ”€ files/ โ”‚ โ””โ”€โ”€ mime.types โ”œโ”€โ”€ vars/ โ”‚ โ””โ”€โ”€ main.yml โ”œโ”€โ”€ defaults/ โ”‚ โ””โ”€โ”€ main.yml # lowest priority variables โ””โ”€โ”€ meta/ โ””โ”€โ”€ main.yml # dependencies # Use role in playbook - hosts: webservers roles: - common - { role: nginx, nginx_port: 8080 } - role: app vars: app_version: "2.1.0" # Install roles from Ansible Galaxy ansible-galaxy install geerlingguy.nginx ansible-galaxy collection install community.general

Ansible Vault

# Encrypt a file ansible-vault encrypt vars/secrets.yml ansible-vault encrypt_string 'mysecretpassword' --name 'db_password' # Edit encrypted file ansible-vault edit vars/secrets.yml # Decrypt file ansible-vault decrypt vars/secrets.yml # Rekey (change password) ansible-vault rekey vars/secrets.yml # Run playbook with vault password ansible-playbook deploy.yml --ask-vault-pass ansible-playbook deploy.yml --vault-password-file ~/.vault_pass # Vault in group_vars # group_vars/production/secrets.yml (encrypted) # db_password: !vault | # $ANSIBLE_VAULT;1.1;AES256 # 6631356... # Multiple vault IDs (Ansible 2.4+) ansible-vault encrypt --vault-id dev@prompt vars/dev.yml ansible-playbook deploy.yml --vault-id dev@~/.dev_pass