¿Por qué Ansible para una flota de VPS?
Cuando se gestionan varios servidores, la tentación natural es escribir scripts de Bash. Es rápido de arrancar, pero los scripts no son idempotentes: ejecútelos dos veces y corre el riesgo de duplicar entradas, sobrescribir archivos o romper una configuración que funcionaba. Fabric mejora la ergonomía de Python, pero sigue en la misma lógica imperativa. Puppet y Chef son herramientas potentes, pero imponen un agente en cada nodo, un servidor maestro que mantener y una curva de aprendizaje considerable para un equipo que solo quiere mantener coherentes sus VPS.
Ansible se posiciona de otra forma. Funciona en modo push, a través de SSH, sin instalar nada en los hosts de destino. Cada playbook describe un estado final en lugar de una secuencia de acciones. Si lo ejecuta una segunda vez en un servidor ya configurado, Ansible no modifica nada: es la propiedad de idempotencia, y resulta fundamental para operar una flota con confianza.
Para una agencia web que entrega proyectos en VPS de clientes, o para un equipo DevOps que estandariza entornos de staging y de producción, Ansible ofrece la relación esfuerzo/beneficio más favorable del mercado: una sintaxis YAML accesible, una comunidad enorme y una integración natural en los pipelines CI/CD existentes.
8 razones para elegir Ansible para sus servidores VPS
- Sin agente, a través de SSH: ningún daemon que instalar en sus hosts. Ansible se conecta por SSH con sus claves existentes, lo que reduce la superficie de ataque y elimina la deuda de mantenimiento ligada a los agentes.
- Idempotencia nativa: cada módulo de Ansible garantiza que volver a ejecutar un playbook en un sistema ya configurado no produzca ningún cambio parásito. Puede ejecutar sus playbooks con total seguridad en una flota en producción.
- Sintaxis YAML legible: los playbooks se leen como documentación. Un desarrollador que no conoce Ansible entiende lo que hace un rol en unos minutos, lo que facilita la revisión de código y la incorporación de nuevos miembros.
- Inventario dinámico: además de los archivos estáticos
hosts.ini, Ansible puede consultar a su proveedor cloud o una API interna para construir el inventario sobre la marcha. Ideal cuando los VPS aparecen y desaparecen con frecuencia. - Roles reutilizables: la estructura
roles/permite empaquetar una configuración (nginx, PostgreSQL, endurecimiento de SSH) y reutilizarla de un proyecto a otro sin copiar y pegar playbooks. - Ansible Vault para los secretos: las contraseñas, claves de API y certificados se cifran directamente en el repositorio Git con
ansible-vault. Se acabaron los secretos en claro en los scripts o en variables de entorno sin versionar. - Ansible Galaxy: un ecosistema de roles comunitarios (geerlingguy, devsec) cubre los casos de uso más habituales. En lugar de escribir un rol de endurecimiento de SSH desde cero, importa uno auditado por miles de usuarios.
- Compatible con CI/CD: un playbook se ejecuta desde un pipeline de GitHub Actions o GitLab CI con exactamente el mismo comando que en local. Cada merge en
mainpuede desencadenar automáticamente el despliegue de la configuración en su flota.
Requisitos previos: lo que necesita antes de empezar
Antes de escribir su primer playbook, conviene comprobar algunos requisitos, tanto en la máquina de control como en los servidores de destino.
En la máquina de control (su equipo local o un VPS dedicado a la orquestación), necesita Python 3.8 o superior y Ansible 2.14 como mínimo. Ansible no funciona de forma nativa en Windows como máquina de control: si usa Windows, recurra a WSL2 o a un contenedor Docker.
En los servidores VPS de destino, los requisitos son mínimos: un acceso SSH con un usuario que disponga de permisos sudo, Python 3 instalado (presente por defecto en Debian 11+, Ubuntu 20.04+ y Rocky Linux 8+), y su clave pública SSH ya desplegada en cada host. Si parte de servidores recién aprovisionados, el acceso root inicial basta para la primera pasada de configuración.
Organice su espacio de trabajo en un repositorio Git desde el principio. Versionar el inventario y los playbooks es la única forma de saber qué configuración se aplicó a qué máquina, y cuándo. Un archivo ansible.cfg en la raíz del proyecto permite centralizar los parámetros (ruta del inventario, usuario remoto, clave SSH) para no repetirlos en la línea de comandos.
De la instalación a su primer playbook en 7 pasos
Instalar Ansible en la máquina de control
El método recomendado es
pip install ansibledentro de un entorno virtual de Python, lo que le da la última versión estable con independencia de su distribución. En Debian/Ubuntu,apt install ansibletambién funciona, pero suele instalar una versión más antigua. Compruebe conansible --versionque la instalación es correcta y anote la ruta hacia la configuración.Crear el inventario con sus grupos de servidores
Cree un archivo
inventory/hosts.iniy organice sus VPS en grupos lógicos:[web]para los servidores de aplicaciones,[db]para las bases de datos,[mail]para los servidores de correo. Cada host se indica por su IP o su nombre DNS, conansible_user=ubuntuen su caso, si el usuario SSH es distinto. Los grupos facilitan la aplicación de roles concretos.Probar la conectividad con el módulo ping
Antes de cualquier playbook, valide que el inventario es correcto y que SSH funciona:
ansible -i inventory/hosts.ini all -m ping. Cada host debe responderpong. Si una máquina falla, revise el nombre de usuario, la clave SSH y que Python 3 esté disponible en el destino. Esta prueba básica le evita depurar un playbook cuando el problema está en el transporte.Escribir un playbook de endurecimiento inicial
Cree
playbooks/hardening.ymlcon tres tareas esenciales: crear un usuario de administración distinto de root con su clave pública, modificarsshd_configpara desactivar la autenticación por contraseña y el acceso root directo, y después configurarufwcon una política por defecto deny y únicamente los puertos autorizados (22, 80, 443). Utilice los módulosuser,lineinfileyufwde Ansible.Ejecutar en modo dry-run con --check
Antes de aplicar el playbook en sus servidores, ejecute
ansible-playbook --check playbooks/hardening.yml. El flag--checksimula la ejecución sin modificar nada: Ansible le indica exactamente qué tareas habrían producido un cambio (changed) y cuáles no habrían hecho nada (ok). Corrija los posibles errores de sintaxis o de lógica antes de la aplicación real.Aplicar y comprobar la idempotencia
Lance el playbook sin
--checkpara la aplicación real. Anote el número de tareaschanged. Vuelva a lanzarlo de inmediato una segunda vez: si su playbook está bien escrito, el contadorchangeddebe quedar a cero. Esta comprobación de idempotencia es el criterio de calidad fundamental de un playbook de Ansible. Un playbook que produce cambios en la segunda ejecución esconde un error de lógica.Refactorizar en un rol reutilizable
Una vez estabilizado el playbook, conviértalo en un rol con
ansible-galaxy init roles/hardening. Traslade las tareas aroles/hardening/tasks/main.yml, las variables por defecto adefaults/main.ymly los handlers (como la recarga desshd) ahandlers/main.yml. El rol se convierte en un bloque reutilizable que puede aplicar a cualquier grupo de hosts desde cualquier proyecto.
Gestionar los secretos con Ansible Vault
En una flota de servidores, los secretos están por todas partes: contraseñas de bases de datos, claves de API de servicios de terceros, certificados TLS, tokens de acceso a los registros Docker. La tentación de almacenarlos en claro en los archivos de variables es fuerte, sobre todo cuando se trabaja en solitario. Es un riesgo importante en cuanto el repositorio pasa a ser compartido o un desarrollador deja el equipo.
Ansible Vault cifra sus archivos de variables directamente en el repositorio Git. El comando ansible-vault create vars/secrets.yml abre un editor y cifra el resultado con una contraseña maestra (o una clave de bóveda). El archivo cifrado se puede versionar con total seguridad: sin la contraseña, su contenido es ilegible.
En un equipo, conviene utilizar un archivo de contraseña (--vault-password-file ~/.vault_pass) en lugar de teclearla en cada ejecución. Ese archivo se almacena fuera del repositorio y se distribuye mediante un gestor de secretos como HashiCorp Vault o su pipeline CI/CD. GitHub Actions y GitLab CI permiten guardar la contraseña de Vault como secreto de entorno, lo que hace que ejecutar los playbooks en el pipeline sea tan sencillo como en local.
Una buena práctica: separe sus variables en dos archivos — vars/main.yml para los valores no sensibles (nombres de dominio, puertos, versiones) y vars/secrets.yml cifrado para los secretos. Sus playbooks leen ambos, y solo secrets.yml requiere el Vault.
Si algunos de sus VPS están detrás de un NAT estricto o de un cortafuegos que bloquea las conexiones SSH entrantes desde su máquina de control, el modo push de Ansible no funciona. La solución es ansible-pull: instale Ansible en cada host de destino y configure un cron o un timer de systemd que ejecute ansible-pull -U <url-del-repositorio> a intervalos regulares. Cada servidor descarga por sí mismo su configuración desde Git y la aplica en local. Es lo contrario del modo habitual, pero la idempotencia y los roles funcionan exactamente igual. También resulta útil en entornos air-gapped donde solo el servidor tiene acceso al repositorio interno.
Ir más lejos: inventario dinámico y AWX
Un inventario estático hosts.ini es perfectamente válido para una flota estable. Pero si aprovisiona y destruye VPS con frecuencia — para entornos de staging efímeros o proyectos de cliente de duración limitada — mantener el archivo a mano se convierte en una fuente de errores.
El inventario dinámico resuelve ese problema: Ansible puede consultar una API (su proveedor cloud, Netbox, un script propio) para construir la lista de hosts sobre la marcha antes de cada ejecución. El plugin community.general.cobbler o un script de Python que devuelva JSON estructurado bastan en la mayoría de los casos.
Para los equipos que quieren una interfaz gráfica y un control de acceso por rol, AWX (la versión open source de Red Hat Ansible Automation Platform) o Semaphore (más ligero, adaptado a equipos pequeños) ofrecen una interfaz web para gestionar los inventarios, lanzar playbooks, programar ejecuciones y auditar las pasadas anteriores. AWX se instala en un VPS dedicado y expone una API REST: puede lanzar un playbook desde un pipeline de CI, desde un webhook o desde un botón de su herramienta interna.
La adopción de estas herramientas marca el paso de una administración personal con Ansible a una práctica de equipo estructurada, donde cada ejecución queda trazada, aprobada y asociada a un usuario identificado.
Conclusión: una infraestructura declarativa y reproducible
Ansible no es una herramienta mágica, pero responde con precisión al problema cotidiano de cualquier equipo que administra varios VPS: ¿cómo asegurarse de que el estado real de cada servidor se corresponde con lo previsto, sin dedicar horas a comparar configuraciones a mano?
Al adoptar un enfoque declarativo — describir lo que quiere en lugar de cómo obtenerlo — gana en reproducibilidad, en trazabilidad y en confianza. Un nuevo colaborador puede entender el estado de su infraestructura leyendo los playbooks. Un servidor que cae puede reconstruirse desde cero en unos minutos con el mismo inventario. Una auditoría de seguridad se convierte en una lectura de YAML en lugar de una inspección máquina por máquina.
Empiece poco a poco: un playbook de endurecimiento inicial aplicado a sus VPS actuales. Versiónelo, pruebe la idempotencia y añada roles a medida que surjan las necesidades. La inversión inicial es modesta, y las ganancias en tiempo y fiabilidad se vuelven evidentes a partir de la segunda o tercera máquina gestionada.