DevPath · Aprende a programar ESPTEN

Producción y despliegue

Despliegue y resiliencia

Apagado ordenado (graceful shutdown)

Cuando despliegas una versión nueva o escalas hacia abajo, la plataforma detiene las instancias viejas. No las mata de golpe: primero les envía la señal SIGTERM para pedirles que terminen ordenadamente. Un proceso bien hecho escucha esa señal y hace un apagado ordenado (graceful shutdown):

  1. Deja de aceptar nuevas peticiones (cierra el servidor HTTP).
  2. Termina las peticiones que ya están en curso.
  3. Cierra los recursos abiertos: conexiones a la base de datos, colas, ficheros.
  4. Sale del proceso (process.exit(0)).
process.on("SIGTERM", async () => {
  console.log("SIGTERM recibido, cerrando...");
  servidor.close();        // 1 y 2: no acepta nuevas, drena las activas
  await db.disconnect();   // 3: cierra la BD
  process.exit(0);         // 4
});

Sin esto, un despliegue cortaría peticiones a medias y dejaría conexiones colgadas. Suele añadirse un timeout: si en, p. ej., 10 segundos no ha terminado, se fuerza la salida para no quedar bloqueado.

Process managers (PM2)

En producción no ejecutas node app.js a mano. Un process manager como PM2 se encarga de:

Contenedores (Docker)

Un contenedor Docker empaqueta tu app con su entorno (versión de Node, dependencias, sistema base) en una imagen inmutable. La misma imagen corre igual en tu portátil y en producción ("funciona en mi máquina" deja de ser una excusa). La config y los secretos se inyectan desde fuera como variables de entorno (coherente con 12-factor), nunca dentro de la imagen.

CI/CD

Un pipeline de CI/CD (GitHub Actions, GitLab CI...) automatiza el camino del commit a producción: en cada push ejecuta los tests y el lint (Continuous Integration) y, si pasan, construye la imagen y la despliega (Continuous Delivery/Deployment). El objetivo es que desplegar sea un evento aburrido y seguro, no un ritual de riesgo.

Escalado horizontal

Para soportar más carga tienes dos vías: vertical (una máquina más grande, con límite físico) y horizontal (más instancias detrás de un balanceador de carga). El escalado horizontal es la base de la alta disponibilidad, pero exige que el servidor sea stateless: no debe guardar estado en memoria (sesiones, caché) que sólo viva en una instancia; ese estado va a un almacén compartido (Redis, la BD). Así cualquier instancia puede atender cualquier petición, y health checks + graceful shutdown permiten añadir y quitar instancias sin que el usuario lo note.

Ejemplos

Esqueleto de graceful shutdown ante SIGTERM

// Simulación: un servidor con un método close y una BD con disconnect.
const servidor = { close() { console.log("Servidor cerrado: no acepta nuevas peticiones"); } };
const db = { async disconnect() { console.log("BD desconectada"); } };

async function apagar(senal) {
  console.log(senal + " recibido, iniciando apagado ordenado...");
  servidor.close();
  await db.disconnect();
  console.log("Apagado completo");
}

await apagar("SIGTERM");
Pon esto en práctica

DevPath es un curso práctico: aquí lees la teoría; en la app la pones en práctica con ejercicios que se ejecutan de verdad, sin conexión.

Empezar gratis en la app →
← Logging y observabilidadVer el módulo →