Webhooks explicados: cargas firmadas y reintentos confiables

Backend2026-10-20TryQuickToolBox

Acabas de integrar una pasarela de pago de terceros o un servicio de CI/CD, y ahora necesitas notificaciones en tiempo real. Los webhooks son la respuesta, pero sin la seguridad y confiabilidad adecuadas, pueden convertirse en una fuente de frustración. Los atacantes pueden falsificar solicitudes y los fallos de red pueden provocar eventos perdidos. En esta guía, veremos cómo proteger los webhooks con cargas firmadas e implementar mecanismos de reintento robustos.

¿Qué son los webhooks?

Los webhooks son callbacks HTTP definidos por el usuario que se activan mediante eventos específicos. Cuando ocurre un evento (por ejemplo, un pago exitoso), el servicio de origen envía una solicitud HTTP POST a una URL que proporcionas, con los datos del evento. Este modelo de inserción es más eficiente que el sondeo y permite reacciones en tiempo real.

Sin embargo, los webhooks presentan dos desafíos: autenticidad (asegurar que la solicitud proviene del remitente esperado) y confiabilidad (asegurar que no se pierdan eventos).

Proteger webhooks con cargas firmadas

Una carga firmada utiliza un secreto compartido entre el remitente y el receptor para crear una firma criptográfica. El remitente incluye esta firma en una cabecera y el receptor la verifica para confirmar la integridad y el origen de la carga.

Cómo funciona la firma HMAC

HMAC (código de autenticación de mensajes basado en hash) es el enfoque estándar. El remitente calcula un HMAC sobre el cuerpo de la solicitud usando el secreto compartido y lo incluye en una cabecera como X-Signature. El receptor recalcula el HMAC y lo compara.

// Ejemplo: Generar una firma en Node.js
const crypto = require('crypto');

function generateSignature(payload, secret) {
  return crypto
    .createHmac('sha256', secret)
    .update(JSON.stringify(payload))
    .digest('hex');
}

// En el lado receptor, verificar:
function verifySignature(payload, secret, receivedSignature) {
  const expected = generateSignature(payload, secret);
  // Usar comparación de tiempo constante para prevenir ataques de temporización
  return crypto.timingSafeEqual(
    Buffer.from(expected, 'hex'),
    Buffer.from(receivedSignature, 'hex')
  );
}

Puntos clave:

Medidas de seguridad adicionales

Implementar reintentos confiables

Las redes no son confiables. Un webhook puede fallar debido a tiempos de espera, errores del servidor o interrupciones temporales. Una estrategia de reintentos robusta asegura la entrega eventual sin saturar tu sistema ni al remitente.

Mejores prácticas de reintento

  1. Retroceso exponencial: Aumenta el retraso entre reintentos (por ejemplo, 1s, 2s, 4s, 8s...).
  2. Límite máximo de reintentos: Limita el número de intentos (por ejemplo, 5) para evitar bucles infinitos.
  3. Cola de mensajes muertos: Después de agotar los reintentos, almacena los eventos fallidos para inspección manual.
  4. Idempotencia: Asegura que procesar el mismo evento varias veces no cause efectos secundarios duplicados.

Idempotencia en la práctica

Incluye un ID de evento único en la carga. En el lado receptor, rastrea los IDs procesados (en una base de datos o caché) e ignora los duplicados. Por ejemplo:

// Pseudocódigo para procesamiento idempotente
if (eventStore.exists(event.id)) {
  return 200; // Ya procesado
}
// Procesar evento...
eventStore.save(event.id);

Manejar fallos con elegancia

Responde rápidamente con un estado 2xx para confirmar la recepción. Si el procesamiento lleva tiempo, encola el evento y procésalo de forma asíncrona. Devuelve 5xx solo para errores transitorios que justifiquen un reintento; para errores permanentes (por ejemplo, carga inválida), devuelve 4xx para evitar reintentos inútiles.

Comparación: Push vs. Poll

Aspecto Webhooks (Push) Sondeo
Latencia Casi en tiempo real Depende del intervalo
Eficiencia Solo envía en eventos Solicitudes constantes
Complejidad Requiere lógica de reintento/seguridad Más simple pero derrochador

Probar tu implementación de webhooks

Usa herramientas como ngrok para exponer tu servidor local y simular entregas de webhooks. Verifica la validación de firmas y el comportamiento de reintento fallando solicitudes intencionalmente.

Preguntas frecuentes

¿Qué es una carga de webhook firmada?

Una carga firmada incluye una firma criptográfica (a menudo HMAC) que permite al receptor verificar la autenticidad e integridad de la solicitud usando un secreto compartido.

¿Cuántas veces debo reintentar un webhook fallido?

No hay un número universal, pero 3–5 reintentos con retroceso exponencial son comunes. Después de eso, registra el fallo para revisión manual.

¿Puedo usar webhooks sin HTTPS?

Técnicamente sí, pero es muy inseguro. Siempre usa HTTPS para prevenir escuchas y ataques de intermediario.

¿Listo para inspeccionar cargas de webhooks? Usa nuestro formateador JSON para imprimir y validar cargas JSON rápidamente.