# Ansible: automatització i gestió de configuracions

# 1. Introducció

**Ansible** és una eina d'automatització de codi obert, desenvolupada originalment per Michael DeHaan el 2012 i actualment mantinguda per Red Hat (IBM). Permet gestionar servidors, desplegar aplicacions i orquestrar tasques d'infraestructura de manera **declarativa**: en comptes d'escriure scripts que indiquin *com* fer les coses pas a pas, es descriu *quin estat final* es vol per al sistema, i Ansible s'encarrega d'aconseguir-lo.

![Ansible logo](https://proferamon.com/tic/imatges/ansible/ansible01.png)

Es fa servir molt en entorns d'administració de sistemes i xarxes per:

- Aprovisionar servidors nous de forma reproduïble.
- Mantenir configuracions consistents entre diverses màquines (per exemple, tots els clients d'una aula).
- Desplegar aplicacions i serveis (web, bases de dades, DNS, DHCP...).
- Aplicar pedaços de seguretat i actualitzacions de manera centralitzada.

> [!NOTE]
> A diferència de Puppet, Chef o SaltStack, Ansible és **agentless**: no cal instal·lar cap programari al node gestionat, només necessita accés SSH i Python.

# 2. Característiques principals

| Característica | Descripció |
|---|----------|
| **Agentless** | No requereix cap dimoni ni agent al node remot; funciona sobre SSH (Linux/Unix) o WinRM (Windows). |
| **Declaratiu** | Els *playbooks* descriuen l'estat desitjat, no els passos exactes. |
| **Idempotent** | Executar el mateix playbook diverses vegades no produeix canvis addicionals si el sistema ja és a l'estat desitjat. |
| **YAML** | Els playbooks es defineixen en fitxers YAML, llegibles i fàcils d'escriure. |
| **Inventaris** | Llistes de servidors organitzats en grups (web, bd, dns...) que es poden gestionar de forma selectiva. |
| **Mòduls** | Centenars de mòduls natius (`apt`, `copy`, `service`, `user`, `template`, `cron`...) i mòduls per a núvol (AWS, Azure, Proxmox...). |
| **Rols** | Forma d'organitzar playbooks reutilitzables i compartibles. |
| **Ansible Galaxy** | Dipòsit públic de rols i col·leccions creats per la comunitat. |
| **Vault** | Sistema d'encriptació integrat per protegir dades confidencials (contrasenyes, claus) dins dels playbooks. |

# 3. Arquitectura bàsica

- **Node de control**: la màquina des d'on s'executa Ansible (per exemple, un servidor de gestió).
- **Nodes gestionats (managed nodes)**: els servidors o clients que es volen configurar. Només necessiten:
  - Un servidor SSH actiu.
  - Python 3 instal·lat (present per defecte a la majoria de distribucions modernes, incloent-hi Ubuntu i Debian).
- **Inventari**: fitxer (INI o YAML) que llista els nodes gestionats, agrupats lògicament.
- **Playbook**: fitxer YAML amb la seqüència de tasques a executar.
- **Mòduls**: unitats de codi que Ansible envia temporalment al node remot, executa i elimina.

# 4. Instal·lació a Ubuntu 26.04 LTS

Ubuntu 26.04 LTS ja inclou Ansible als seus dipòsits oficials (paquets `ansible` i `ansible-core`), de manera que en la majoria de casos n'hi ha prou amb:

Actualitza la llista de paquets:

```bash
sudo apt update
```

Instal·la Ansible:

```bash
sudo apt install ansible
```

Comprova la instal·lació:

```bash
ansible --version
```

## 4.1. Instal·lació via PPA (versió més recent)

Els repositoris oficials d'Ubuntu ofereixen la versió que hi havia disponible en el moment d'empaquetar la distribució, i només rep pedaços de seguretat. Si necessites la darrera versió estable amb mòduls i correccions més recents, pots afegir el PPA oficial del projecte, que ja publica paquets per a "Resolute Raccoon" (26.04):

```bash
sudo apt install software-properties-common -y
sudo add-apt-repository --yes --update ppa:ansible/ansible
sudo apt install ansible -y
```

## 4.2. Només `ansible-core` (instal·lació mínima)

Si només necessites el motor sense la col·lecció completa de mòduls de la comunitat (paquet `ansible`, molt més pesat):

```bash
sudo apt install ansible-core
```

# 5. Configuració bàsica

## 5.1. Autenticació SSH sense contrasenya

Ansible funciona millor amb autenticació per clau pública. Des del node de control:

Genera la clau:

```bash
ssh-keygen -t ed25519 -C "ansible@control"
```

Copia la clau:

```bash
ssh-copy-id <usuari>@<node-remot>
```

## 5.2. Fitxer d'inventari

Per defecte, Ansible llegeix `/etc/ansible/hosts`, però és bona pràctica crear un inventari propi per cada projecte. Exemple (`inventory.ini`):

```ini
[servidors_web]
www1.thos.local
www2.thos.local

[servidors_bd]
bd1.thos.local

[laboratori:children]
servidors_web
servidors_bd

[laboratori:vars]
ansible_user=admin
ansible_python_interpreter=/usr/bin/python3
```

## 5.3. Fitxer `ansible.cfg`

Crea un `ansible.cfg` al directori del projecte per personalitzar el comportament (evita haver de passar paràmetres cada cop):

```ini
[defaults]
inventory = ./inventory.ini
remote_user = admin
host_key_checking = False
retry_files_enabled = False
```

## 5.4. Primera prova de connectivitat

```bash
ansible laboratori -i inventory.ini -m ping
```

Si tot és correcte, cada host respondrà amb `"ping": "pong"`.

# 6. Playbooks

Un playbook és un fitxer YAML amb una llista d'una o més "plays". Cada play s'aplica a un grup de l'inventari i conté una llista de tasques.

Exemple: instal·lar i activar Apache als servidors web del laboratori.

```yaml
---
- name: Configurar servidors web
  hosts: servidors_web
  become: true

  tasks:
    - name: Actualitzar la memòria cau d'apt
      apt:
        update_cache: true
        cache_valid_time: 3600

    - name: Instal·lar apache2
      apt:
        name: apache2
        state: present

    - name: Copiar la pàgina d'inici personalitzada
      copy:
        src: files/index.html
        dest: /var/www/html/index.html

    - name: Assegurar que apache2 estigui actiu i habilitat
      service:
        name: apache2
        state: started
        enabled: true

    - name: Obrir el port 80 al tallafoc (UFW)
      ufw:
        rule: allow
        port: "80"
        proto: tcp
```

Executar el playbook:

```bash
ansible-playbook -i inventory.ini playbook.yml
```

Opcions útils:

```bash
ansible-playbook -i inventory.ini playbook.yml --check   # simulació (dry-run)
ansible-playbook -i inventory.ini playbook.yml --diff    # mostra els canvis
ansible-playbook -i inventory.ini playbook.yml --limit www1.thos.local
```

# 7. Variables i plantilles (Jinja2)

Ansible permet fer servir variables i plantilles Jinja2 per generar fitxers de configuració dinàmicament, molt útil per exemple per generar fitxers de zona BIND9 o configuracions de Kea DHCP diferents segons el host.

```yaml
- name: Generar fitxer de configuració
  template:
    src: templates/dhcpd.conf.j2
    dest: /etc/kea/kea-dhcp4.conf
  notify: Reiniciar kea-dhcp4
```

```yaml
handlers:
  - name: Reiniciar kea-dhcp4
    service:
      name: kea-dhcp4-server
      state: restarted
```

# 8. Rols

Els rols permeten organitzar playbooks grans en components reutilitzables, amb una estructura de directoris estàndard:

```bash
ansible-galaxy init rols/apache
```

Genera:

```ini
rols/apache/
├── tasks/
│   └── main.yml
├── handlers/
│   └── main.yml
├── templates/
├── files/
├── vars/
├── defaults/
└── meta/
```

I s'invoquen des d'un playbook així:

```yaml
- hosts: servidors_web
  roles:
    - apache
    - firewall
```

# 9. Ansible Vault (dades confidencials)

Per xifrar contrasenyes o claus dins dels playbooks:

```bash
ansible-vault create secrets.yml
ansible-vault edit secrets.yml
ansible-playbook playbook.yml --ask-vault-pass
```

# 10. Referències i documentació oficial

- Documentació oficial: <https://docs.ansible.com/>
- Guia d'instal·lació per distribució: <https://docs.ansible.com/projects/ansible/latest/installation_guide/installation_distros.html>
- Ansible Galaxy (rols i col·leccions de la comunitat): <https://galaxy.ansible.com/>
- Codi font al GitHub: <https://github.com/ansible/ansible>
- PPA oficial per a Ubuntu: <https://launchpad.net/~ansible/+archive/ubuntu/ansible>
- Referència de mòduls: <https://docs.ansible.com/projects/ansible/latest/collections/index_module.html>

#### Versions d'aquest document

> + [HTML](https://proferamon.com/tic/ansible.html)
> + [PDF](https://proferamon.com/tic/pdf/ansible.pdf)
> + [ODT](https://proferamon.com/tic/odt/ansible.odt)
> + [MD](https://proferamon.com/tic/md/ansible.md)

[Domini Públic (CC0)](https://creativecommons.org/publicdomain/zero/1.0/deed.ca)