Marcio Cunha

Orquestación de Pruebas de Humo en Infraestructura Efímera con Terraform y Terratest

Aprenda a aprovisionar entornos temporales y validar la integridad de sistemas distribuidos antes del despliegue utilizando Terraform y Terratest en flujos de integración continua.

Marcio Cunha•5 min
También disponible en:EnglishPortuguês
Resumen
  • Las infraestructuras efímeras eliminan el problema del estado corrupto al destruir el entorno justo después de la validación.
  • Terratest permite escribir pruebas automatizadas en lenguaje Go para infraestructura como código de forma programática.
  • Las pruebas de humo garantizan que los servicios esenciales respondan correctamente justo después del aprovisionamiento inicial.
  • La integración continua ejecuta validaciones completas sin contaminar el clúster de producción con recursos huérfanos.
  • El uso combinado de Terraform y pruebas integradas reduce drásticamente el tiempo medio de detección de fallos en despliegues.

El Desafío de Validar Entornos que Nacen y Mueren

En la ingeniería de software moderna, aprovisionar servidores manualmente quedó en el pasado. Hoy utilizamos la infraestructura como código, o IaC, lo que significa escribir archivos de texto para describir servidores, redes y bases de dados. Con esto, creamos el concepto de infraestructura efímera: entornos enteros que nacen bajo demanda para un propósito específico, como ejecutar pruebas automatizadas, y luego desaparecen sin dejar rastro.

En la práctica, esto evita que una prueba falle porque sobró basura de una ejecución anterior. Sin embargo, surge un nuevo desafío: cómo garantizar que el entorno recién creado realmente funciona antes de liberar el tráfico de producción? Aquí es donde entran las pruebas de humo, un concepto empleado originalmente en la electrónica para verificar si un circuito largaba humo al encenderlo por primera vez, indicando un cortocircuito grave.

En el desarrollo de software, una prueba de humo es una verificación rápida y superficial de las funcionalidades más críticas de un sistema. Cuando se aplican a la infraestructura efímera, verifican si los servidores respondieron, si las bases de datos aceptan conexiones y si las rutas de red están activas. Sin esta automatización, los equipos pierden horas investigando fallos que podrían evitarse con validaciones programáticas justo en el primer inicio.

La Elección de las Herramientas: Terraform y Terratest

Para poner esta estrategia en práctica, elegimos dos herramientas consagradas en el ecosistema corporativo: Terraform y Terratest. Terraform, creado por HashiCorp, es la herramienta líder para gestionar recursos en la nube de forma declarativa, permitiendo construir y destruir toda la arquitectura con comandos simples en la terminal. Lee nuestros archivos de configuración y se comunica con proveedores como AWS, Google Cloud o Azure.

Por otro lado, Terratest es una biblioteca escrita en Go, desarrollada por Gruntwork, especializada en probar código de infraestructura. Mientras Terraform solo crea recursos, Terratest puede ejecutar comandos de verificación inmediatamente después. En la práctica, actúa como un inspector de obras riguroso que entra al edificio recién construido para probar si las puertas abren y si el agua corre por las canillas antes de entregar las llaves al residente.

El uso conjunto de estas herramientas forma un ciclo virtuoso de seguridad y velocidad. El pipeline de integración continua dispara la creación del entorno temporal mediante Terraform, Terratest valida que todo esté en su lugar y respondiendo, y justo después el propio pipeline destruye el entorno para ahorrar costos. Si cualquier paso falla, el proceso se detiene inmediatamente, evitando que cambios incorrectos avancen hacia los entornos compartidos.

Escribiendo el Código de Aprovisionamiento y Validación

Para entender el flujo en la práctica, necesitamos estructurar nuestro proyecto dividiéndolo entre los archivos de infraestructura y los scripts de prueba. Comenzamos creando un módulo de Terraform básico que levanta una instancia de servidor aislada en la nube con una aplicación web simple instalada. Este archivo define el tipo de máquina, las reglas de seguridad de red y el script inicial que inicializa el servicio.

A continuación, escribimos el código de prueba utilizando el lenguaje Go y la biblioteca Terratest. La prueba debe seguir una secuencia lógica rigurosa de ejecución para garantizar que el entorno esté totalmente listo antes de realizar las peticiones HTTP de validación. A continuación se muestra un ejemplo funcional de cómo se comporta esta estructura en el directorio de pruebas del proyecto.

package test

import (
	"testing"
	"time"
	"github.com/gruntwork-io/terratest/modules/terraform"
	"github.com/gruntwork-io/terratest/modules/http-helper"
)

func TestTerraformAwsWebExample(t *testing.T) {
	terraformOptions := &terraform.Options{
		TerraformDir: "../examples/terraform-basic",
	}

	defer terraform.Destroy(t, terraformOptions)

	terraform.InitAndApply(t, terraformOptions)

	publicIp := terraform.Output(t, terraformOptions, "public_ip")
	url := "http://" + publicIp + ":80"

	http-helper.HttpGetWithRetry(t, url, nil, 200, "Hello, World!", 30, 5*time.Second)
}

En este fragmento de código, la función de prueba inicializa Terraform, aplica la configuración para levantar el servidor, captura la dirección IP pública generada y utiliza un asistente HTTP para intentar acceder a la página web repetidamente hasta obtener un código de estado doscientos. El comando para destruir los recursos está garantizado al final de la ejecución mediante un comando de aplazamiento, lo que asegura que ningún servidor se quede ejecutando y generando costos indebidos.

Integrando el Ciclo de Vida en el Pipeline de CI/CD

Crear el código de prueba localmente es solo el primer paso; el verdadero valor de este enfoque aparece cuando insertamos el proceso en un pipeline de integración continua, como GitHub Actions o GitLab CI. El servidor de automatización necesita tener instaladas las herramientas necesarias, como el intérprete del lenguaje Go, la CLI de Terraform y credenciales válidas de acceso a la nube.

Durante cada envío de código al repositorio, el pipeline ejecuta el comando de pruebas automatizadas. En la práctica, esto significa que cualquier cambio en las configuraciones de red, en las políticas de seguridad o en las versiones del sistema operativo pasará por el filtro de Terratest antes de ser aceptado en la rama principal. Esto elimina el factor humano de olvidar probar una modificación crítica de infraestructura.

Más allá de la seguridad, esta práctica transforma la documentación del proyecto. Como el código de prueba describe exactamente el comportamiento esperado de la infraestructura, los nuevos ingenieros pueden entender rápidamente qué puertos deben estar abiertos y qué respuestas HTTP necesita devolver la aplicación. El código pasa a ser la única fuente de verdad, uniendo desarrollo, operaciones y garantía de calidad en un flujo unificado.

Consideraciones Finales sobre Resiliencia Operacional

La adopción de infraestructura efímera combinada con pruebas automatizadas mediante Terraform y Terratest representa un cambio profundo en la madurez operacional de los equipos de tecnología. Al tratar la infraestructura con el mismo rigor de código aplicado al desarrollo de software tradicional, eliminamos la famosa excusa de que el sistema solo funcionaba en la máquina del desarrollador.

Aunque existe una curva de aprendizaje inicial para dominar el lenguaje Go y la sintaxis de las pruebas, el retorno de la inversión se paga rápidamente con la reducción drástica de incidentes en producción. Los sistemas que nacen probados y mueren poco después garantizan un ciclo de entrega continua mucho más seguro, previsible y escalable para empresas de cualquier tamaño.