Niveles de automatización
Hace poco escribí un twit sobre los niveles de automatización. Desgraciadamente, en 140 caracteres no podía meter todo lo que me gustaría y tampoco podía corregir el error cometido, a pesar de ser importante. Aunque parece que nadie se dio cuenta :D
Pero para eso tengo mi blog.
Aquí contaré cómo veo yo los distintos niveles de automatización, desde la automatización más básica a la más avanzada, con ejemplos y software que puede ayudar a obtener ese nivel.
Faltarán cosas… Sobre todo programas. Agradecería si pudiérais completarlo en comentarios. Si es software privativo, es bienvenido si la entrada no es publicidad cantosa; pero si es libre, mucho mejor.
Estructura
Desgraciadamente, los niveles no son lineales. O al menos, no del todo.
De hecho, habrá ciertos niveles que nunca se puedan alcanzar, como acciones que se realizan una única vez, que no estarán dentro de un cron (aunque es posible que estén dentro de Puppet y éste, dentro de cron).
Por ello, puede decirse que la automatización sigue este esquema:
|
|
Niveles
Nivel 1: Documentación
El nivel más básico de automatización es la documentación. ¿Quién no le ha mandado a un amigo unas instrucciones sobre cómo debe hacer algo?
Podría decirse que ésta es la razón de que creara este blog: documentar cosas típicas que me voy encontrando para no tener que repetirlas. Creo que desde entonces ha evolucionado un poco :D
Es habitual que todo el software de usuario incluya documentación enumerando paso a paso cómo hacer algo. Éste es el espíritu del nivel documental. Manuales de usuario, FAQs, tutoriales, etc.
Problemas de la documentación:
- Puede quedarse obsoleta. Es lógico, ya que…
- … casi nunca se puede probar.
- Es propensa a errores. Imagine un operario de una central nuclear leyendo el manual ante una alerta de fusión del núcleo; lo más probable es que lea deprisa y puede saltarse pasos importantes.
- Es aburrida. ¿Quién se ha leído el manual de su reloj?
- Habitualmente, no tiene control de versiones, ya que se usan formatos como Word, PDF, etc. en lugar de formatos tipo texto.
- Es lento, y si hay que repetirlo, requerirá casi el mismo tiempo que la primera vez.
Para ayudarnos tenemos distintas herramientas de generación de documentación, como Sphinx, Javadoc o más genérica, como Doxygen.
Nivel 2: Script
Si tenemos un tutorial que indica paso por paso cómo instalar un programa… ¿Por qué no scriptarlo? Basta con transformar cada uno de esos puntos en una función de un script e invocar a cada una de estas funciones de manera secuencial. Es decir: basta con formalizar la documentación.
Ejemplos de software en este nivel son todos los programas de instalación, ya que van paso por paso ejecutando acciones. Algunas veces requieren la acción del usuario para tomar decisiones o para introducir algún valor.
Este nivel tiene algunas ventajas sobre el de documentación:
- Se puede probar.
- No es propenso a errores, al menos para el flujo básico. Si funciona una vez, el ordenador no se saltará pasos ni los hará en distinto orden.
- No requiere acción por parte del usuario, más allá de saber si requiere algún parámetro o saber responder alguna pregunta.
- Puede meterse en un control de versiones.
- Se puede distribuir a otras máquinas, es decir, es replicable.
- Ahorra tiempo. Una vez escrito, no es necesario saber qué hace por dentro (¿Alguien sabe qué ocurre al hacer un
git init
?)
Sin embargo, también tiene problemas:
- Requiere la presencia del usuario.
- Su replicación, habitualmente requerirá documentación, devolviéndonos al nivel anterior.
- Puede quedarse obsoleto. Que se pueda probar no significa que haya pruebas ni que alguien lo pruebe.
Estos tres problemas son, exactamente, los que se tratan de solucionar en el nivel siguiente.
Nivel 3: Script automatizado
En este nivel hay 3 partes. No tienen por qué cumplirse las 3 y tampoco tienen que hacerse en un orden determinado. Pero son 3 partes bien diferenciadas que conviene identificar:
Nivel 3.1: Temporización
Con el fin de evitar la presencia del usuario, se pueden utilizar archivos de configuración y provocar que nuestro script se ejecute cada cierto intervalo de tiempo.
Para esta tarea suele puede utilizar cron, at o anacron.
Este conocimiento hubiera facilitado mucho la vida de Desmond en la isla de Perdidos (Lost) :D.
Nivel 3.2: Replicabilidad
No sé cómo llamar a este nivel. Hay gente que se refiere a él como “orquestación”, pero no estoy hablando de la gestión de numerosas máquinas, sino de la realización de pequeñas acciones. Claro, que es la realización de estas pequeñas acciones las que permiten esos sistemas dignos de ser orquestados.
La distribución de nuestro script en distintas máquinas puede implicar distintas cosas: Puede ser una distribución para que el usuario lo instale (como hacen las conocidas App Stores) o de manera automática (Puppet, Chef, SaltStack, …).
Estamos hablando de automatización, así que me centraré en esta última: cuando la distribución es automática, también puede serlo su ejecución, en cuyo caso este nivel podría englobar también el de Temporización.
La decisión podríamos estar tomándola cuando utilizamos el software de orquestación: ¿Debe ser Puppet quien lo ejecute o sólo debe instalarlo en un cron?
Cuando hablo de “replicabilidad” no me refiero sólo a la distribución, sino a asegurar que no ocurre el efecto “en mi máquina funciona”. Una forma de conseguir replicabilidad es utilizar un sistema de “jaulas” con todo el sistema, de manera que se ejecuten entornos aislados como un todo. Para ello se pueden utilizar Máquinas virtuales(VirtualBox, Vagrant, …), containers (lxc, Docker o, a menor escala, VirtualEnv, Bundle) o simples listas de instalación (pip, bower, …).
La gestión de estos entornos aislados dan para otro post. Pueden ser de distintos tipos:
- Gestión de artefactos específicos, como puede ser un repositorio Debian, compatible con la aplicación cliente (apt).
- Gestión de artefactos genéricos, como Nexus, Artifactory, …
- Gestión y creación de máquinas virtuales y sistemas de red completos: Mesos.
Nivel 3.3: Monitorización y alertas
Puede considerarse la ejecución del script como una prueba del mismo. Por lo tanto, ¿por qué no monitorizarlo?
La monitorización con alertas nos avisará en dos circunstancias: cuando el elemento monitorizado no tiene los valores que debe o bien cuando el script que obtiene ese valor da problemas. Es como tener un téster constante.
La monitorización puede tener distintas formas, de más sencilla a más compleja:
- Comprobación de que el proceso está corriendo.
- Comprobación de un puerto o del efecto que debe producir el script.
- Lectura de los archivos de log para comprobar que van cambiando de la manera esperada.
- Generación de estadísticas y posterior comprobación de las mismas para ver tendencias.
Y lo mismo ocurre con las alertas:
- Una alarma todo va bien de Homer Simpsom, que nos mande un mail cada vez que acaba de manera exitosa. Esto requiere una comprobación manual que nos devuelve al nivel 1 :D
- Un sistema cliente/servidor con interfaz web, como pueda ser Nagios, Icinga, Pandora, Zabbix, Sensu, Riemann, Cabot, …
- Un sistema distinto para monitorización (Munin, …) y alertas (FlapJack, …)
- Un sistema de agrupación de datos (Graphite), monitorización sobre el mismo y alertas.
Y también con la forma de las alertas: mail, alerta en un panel, SMS, llamada pregrabada, servicio de mensajería instantánea, tícket, etc.
El tema de la monitorización y alertado es toda una ciencia, ya que puede tener numerosas implicaciones: servicios de 24x7, guardias, releases con alertas a ignorar, …
Un sistema de alertas deficiente puede provocar dos efectos nocivos:
- Que se pierdan alertas, de manera que un proceso crítico no esté atendido. Es algo que ocurrirá tarde o temprano, y la solución es añadir una alerta nueva.
- Que lleguen demasiadas alertas, de manera que las críticas se mezclan con las normales. Es mucho peor que el anterior y la solución no suele ser nada sencilla.
Nivel 3.4: Autorecovery
Pero… ¿Qué ocurre cuando llega una alerta?
Pues que entra en marcha un nuevo proceso automatizable: la resolución.
Ésta puede ser:
- Completamente manual: llega la alerta y hay que investigar dónde está el problema.
- Documentada: junto con la alerta llega la solución (o una URL con la misma).
- Automática: al recibir la alerta, se lanza un proceso que intenta recuperarse del problema.
Algunas medidas que pueden tomarse:
- Si es un servicio y se ha muerto, puede volver a lanzarse.
- Si es un servicio y no responde en un puerto, quizá pueda reiniciarse.
- Si es una máquina que no responde, quizá dispongamos de alta disponibilidad (High Availability) y otro servidor pueda ocupar su lugar.
- Si tenemos balanceo de carga y el sistema está sobredimensionado, es posible que no se requiera acción inmediata.
También hay software que nos ayuda en este caso: supervisord, HAProxy, KeepAlive, Monit, …
Es importante que el autorecovery quede documentado de alguna manera. De esta forma se pueden indentificar fallos periódicos (por ejemplo, “el servidor se cae todos los días a las 00:00”). Este registro puede tener la forma de mail, log, etc.
Es más: Si se puede mezclar la hora del autorecovery con el resto de gráficas, mucho mejor, de manera que se quede automáticamente aclarado un problema; por ejemplo, que un pico de la gráfica de memoria se debe a un reinicio de tal servicio.
Nivel 4: Sistemas autónomos
Este artículo puede leerse de dos maneras. La primera es leerlo como la automatización de un script, y la segunda, como un sistema considerablemente más grande: una máquina, una red, una organización.
El todo se compone de cada una de las partes.
En el caso de un script, una vez es distribuido automáticamente y monitorizado, la automatización ya es completa.
Sin embargo, en el caso de una máquina aún falta otro detalle: Si es necesario entrar a la máquina para algo, entonces aún no se ha automatizado completamente. Esto tiene muchas implicaciones:
- Debe existir un sistema de logs centralizado y externo al sistema autónomo. Una solución típica es usar logstash + elastic search + kibana para guardar los logs y rsyslog para enviar los logs del sistema.
- El sistema de monitorización y alertas debe ser igualmente centralizado y externo al sistema autónomo.
- El despliegue de todos los servicios del sistema autónomo debe ser automático.
- Deben existir políticas de autorecovery muy fuertes.
Nomenclatura
Propongo medir el nivel de automatización de un sistema mediante la siguiente nomenclatura:
- El literal “A”, de “Automation”
- Un número, indicando el nivel.
- En el caso del nivel 3, un conjunto de letras, siendo ’t’ para temporización, ‘r’ para Replicación, ’m’ para monitorización y ‘a’ para autorecovery. De esta manera se pueden combinar en ’ta’ para autorecovery y temporización, etc. En este caso es importante seguir el orden: ’t’, ‘r’, ’m’, ‘a’.
Aquí está la tabla completa de nomenclatura
Código | Significado |
---|---|
A0 | No tiene ningún tipo de automatización |
A1 | Hay documentación |
A2 | Existe un script para hacer el trabajo |
A3.t | El script se ejecuta cada cierto tiempo |
A3.r | El script se replica a otras máquinas |
A3.m | Existe monitorización |
A3.a | Existe autorecovery |
A3.tr | El script se replica a otras máquinas y ejecuta cada cierto tiempo |
A3.tm | El script se ejecuta cada cierto tiempo y está monitorizado |
A3.ta | El script se ejecuta cada cierto tiempo y en caso de fallo se arregla sólo |
A3.rm | El script se replica a otras máquinas y está temporizado |
A3.ra | El script se replica a otras máquinas y tiene autorecovery |
A3.ma | El script tiene monitorización y autorecovery |
A3.trm | Temporización, replicación y monitorización |
A3.tra | Temporización, replicación y autorecovery |
A3.tma | Temporización, monitorización y autorecovery |
A3.rma | Replicación, monitorización y autorecovery |
A3.trma | Temporización, Replicación, monitorización y autorecovery |
A4 | Sistema autónomo |
De esta manera se pueden especificar los KPI (Key Performance Indicator) de la siguiente forma: “Conseguir A2 en el build y A3.rm en el despliegue”.
Conclusiones
Montar un sistema autónomo es difícil, pero las ventajas son enormes. A mayor automatización, mayor velocidad en el resto de procesos. Si un push en un repositorio desencadena todo un flujo de tareas que termina en el despliegue en producción o en una alerta en mi buzón si hay algún error, provocará que cada trabajador pueda publicar decenas de versiones en un solo día, y que las implicaciones de los errores sean mucho menores.
El otro día hablaba con David y me decía que “el software está vivo”. Es una gran verdad que hay que tener en cuenta a la hora de diseñar nuestro sistema automático: debe ser propenso al cambio.
Ésta es una diferencia entre los administradores de sistemas actuales y los de antaño: hoy día deben abrazar los principios del manifiesto ágil y abrazar el cambio. Se acabó lo de “si funciona no lo toques”.