GH GambleHub

Webhooks: repeticiones y recibos

1) Modelo de envío básico

At-least-once (predeterminado): el evento se entregará ≥1 vez. Las garantías son alcanzadas suavemente-una-vez por la idempotencia del receptor.
Recibo (ACK): sólo cualquier 2xx (normalmente 200/204) del destinatario significa éxito. Todo lo demás se interpreta como rechazo y conduce a la repetición.
ACK rápido: responda 2xx después de colocar el evento a su vez, no después del procesamiento empresarial completo.

2) Formato de eventos y títulos obligatorios

Carga útil (ejemplo)

json
{
"id": "evt_01HXYZ",
"type": "order. created",
"occurred_at": "2025-11-03T18:10:12Z",
"sequence": 128374,
"source": "orders",
"data": { "order_id": "o_123", "amount": "49. 90", "currency": "EUR" },
"schema_version": 1
}

Encabezados del remitente

'X-Webhook-Id: evt_01HXYZ' es un ID de evento único (use para deduplicación).
'X-Webhook-Seq: 128374' es una secuencia monótona (por suscripción/tema).
`X-Signature: sha256=<base64(hmac_sha256(body, secret))>` — HMAC-подпись.
'X-Retry: 0,1,2...' es el número de intento.
'X-Webhook-Versión: 1' - versionar el contrato.
(opcional) 'Traceparent' es una correlación de pistas.

Respuesta

2xx - aceptado con éxito (no habrá más repeticiones de este 'id').
410 Gone - endpoint está eliminado/inactivo → el remitente detiene las repeticiones y desactiva la suscripción.
429/5xx/timaut - el remitente repite por política de retraídas.

3) Política de repetición (retries)

Escalera recomendada backoff (+ jitter)

'1s, 3s, 10s, 30s, 2m, 10m, 30m, 2h, 6h, 24h' (detenemos después del límite, por ejemplo 48-72 horas).

Reglas:
  • Backoff exponencial + jitter aleatorio (± 20-30%) para evitar el «efecto manada».
  • Quórum de errores para fallas temporales (por ejemplo, repetición si 5xx o tiempo de espera de red).
  • Respuesta 429: ponga un mínimo de 'min (título Retry-After, siguiente ventana backoff)'.

Tamaños y tamaños

Tiempo de espera de conexión ≤ 3-5 segundos; tiempo de respuesta total ≤ 10 segundos.
El tamaño del cuerpo por contrato (por ejemplo, ≤ 256 KB), de lo contrario 413 → la lógica «chunking» o «pull URL».

4) Idempotencia y deduplicación

Aplicación idempotente: el procesamiento de repeticiones del mismo 'id' debe devolver el mismo resultado y no cambiar el estado de nuevo.
Almacenamiento de información en el lado del destinatario: almacenar '(X-Webhook-Id, processed_at, checksum)' con TTL ≥ ventanas retraídas (24-72 h).
Clave compositiva: si varios topics → '(subscription_id, event_id)'.

5) Orden y «exactly-once efectos»

Es difícil garantizar un orden estricto en los sistemas distribuidos. Utilice:
  • Partition by key: el mismo conjunto lógico (por ejemplo, 'order _ id') siempre está en el mismo «canal» de entrega.
  • Sequence: rechaza los eventos con el antiguo 'X-Webhook-Seq' y póngalos en un 'parking lot' antes de que lleguen los que faltan.
Exactly-once efectos se consiguen a través de:
  • registro de las operaciones aplicadas (outbox/inbox pattern),
  • upsert transaccional por 'event _ id' en DB,
  • sagas/compensaciones para procesos complejos.

6) Solución de errores de código de estado (tabla)

Código de respuestaValor del remitenteAcción
2xxACK recibidoCreemos que entregada, detenemos el retiro
4xx (excepto 410/429)Error persistente (payload/autorización)Poner en DLQ, notificar la integración
410Endpoint eliminado/obsoletoDetener retraídas, desactivar la suscripción
408/429Sobrecarga temporal/temporizaciónRepetición por backoff/Jitter; tener en cuenta 'Retry-After'
5xxError temporal del servidorRepetición por backoff/Jitter
3xxNo utilice redirecciones para webhooksInterpretar como error de configuración

7) Seguridad del canal

Firma HMAC de cada mensaje; comprobación en el receptor con «ventana de tiempo» (mitm y replay-ataque).
mTLS para dominios sensibles (CUS/pagos).
IP allowlist de direcciones salientes, TLS 1. 2+, HSTS.
Minimización PII: no envíe datos personales superfluos; enmascarar en las guarniciones.
Rotación de secretos: dos claves activas (active/next) y un encabezado 'X-Key-Id' para indicar la actual.

8) Colas, DLQ y réplicas

Los eventos se escriben necesariamente en una cola de salida/registro en el lado del remitente (para una reproducción confiable).
Cuando se supera el máximo de retraídas, el evento se va al DLQ (Dead Letter Queue) con la causa.
Replay API (para destinatario/operador): volver a enviar por 'id '/intervalo de tiempo/tema, con límite de RPS y firma/autorización adicional.

Ejemplo de API de respuesta (remitente):

POST /v1/webhooks/replay
{ "subscription_id": "sub_123", "from": "2025-11-03T00:00:00Z", "to": "2025-11-03T12:00:00Z" }
→ 202 Accepted

9) Contrato y versión

Versione el evento (campo 'schema _ version') y el transporte ('X-Webhook-Version').
Agregue campos sólo como opcionales; cuando se elimina, migración menor y período de transición (dual-write).
Documente tipos de eventos, ejemplos, esquemas (JSON Schema), códigos de error.

10) Observabilidad y SLO

Métricas clave del remitente:
  • 'delivery _ success _ rate' (2xx/todos los intentos), 'first _ attempt _ success _ rate'
  • `retries_total`, `max_retry_age_seconds`, `dlq_count`
  • `latency_p50/p95` (occurred_at → ack_received_at)
Métricas clave del destinatario:
  • `ack_latency` (receive → 2xx), `processing_latency` (enqueue → done)
  • `duplicates_total`, `invalid_signature_total`, `out_of_order_total`
Ejemplos de SLO:

99. El 9% de los eventos reciben el primer ACK ≤ 60 segundos (28d).

  • DLQ ≤ 0. 1% del total; réplica DLQ ≤ 24 h.

11) Tiempo de espera y roturas de red

Utilice UTC en los campos de tiempo; sincronizar NTP.
Envíe 'occurred _ at' y confirme 'delivered _ at' para contar el trago.
Con interrupciones prolongadas, la red/endpoint → acumular en la cola, limitar el crecimiento (backpressure + cuotas).

12) Límites recomendados e higiene

RPS de suscripción (por ejemplo, 50 RPS, burst 100) + paralelismo (por ejemplo, 10).
Max. cuerpo: 64-256 KB; para más - «notification + URL» y la firma de descarga.
Nombres de eventos en 'snake. case 'o' dot. type` (`order. created`).
Idempotencia estricta de las operaciones de escritura del receptor.

13) Ejemplos: remitente y destinatario

13. 1 Remitente (pseudocódigo)

python def send_event(event, attempt=0):
body = json. dumps(event)
sig = hmac_sha256_base64(body, secret)
headers = {
"X-Webhook-Id": event["id"],
"X-Webhook-Seq": str(event["sequence"]),
"X-Retry": str(attempt),
"X-Signature": f"sha256={sig}",
"Content-Type": "application/json"
}
res = http. post(endpoint, body, headers, timeout=10)
if 200 <= res. status < 300:
mark_delivered(event["id"])
elif res. status == 410:
deactivate_subscription()
else:
schedule_retry(event, attempt+1) # backoff + jitter, respect 429 Retry-After

13. 2 Destinatario (pseudocódigo)

python
@app. post("/webhooks")
def handle():
body  = request. data headers = request. headers assert verify_hmac(body, headers["X-Signature"], secret)
evt_id = headers["X-Webhook-Id"]
if dedup_store. exists(evt_id):
return, "" 204 enqueue_for_processing (body) # fast path. dedup_store put(evt_id, ttl=723600)
return, "" 202 # or 204

14) Pruebas y prácticas de caos

Casos negativos: firma invisible, 429/5xx, timaut, 410, grandes payload's.
Conductual: fuera de orden, duplicados, retrasos de 1-10 minutos, brecha de 24 horas.
Carga: burst 10 ×; compruebe la backpressure y la estabilidad de DLQ.
Contratos: JSON Schema, títulos obligatorios, tipos de eventos estables.

15) Lista de verificación de implementación

  • 2xx = ACK, y un retorno rápido después de enqueue
  • Exponencial backoff + jitter, respeto 'Retry-After'
  • Idempotencia del receptor y del dedoop por 'X-Webhook-Id' (TTL ≥ retrae)
  • Firmas HMAC, rotación de secretos, optional mTLS
  • DLQ + Replay API, monitoreo y alertas
  • Restricciones: temporizadores, RPS, tamaño del cuerpo
  • Orden: partition by key o 'sequence' + «parking lot»
  • Documentación: esquemas, ejemplos, codificaciones de errores, versiones
  • Pruebas de caos: retrasos, tomas, fallo de red, replay prolongado

16) Mini preguntas frecuentes

¿Siempre tienes que responder 200?
Cualquier 2xx se cuenta como un éxito. 202/204 es una práctica normal para «aceptada en la cola».

¿Es posible detener las repeticiones?
Sí, respuesta 410 y/o a través de la consola/API del remitente (desconexión de suscripción).

¿Qué pasa con los grandes payload 'ami?
Envía una «notificación + URL segura», firma la solicitud de descarga e instala la TTL.

¿Cómo puedo mantener el orden?
Partition by key + `sequence`; en caso de discrepancia, «parking lot» y rejuvenecimiento.

Resultado

Los webhooks confiables son una clara semántica ACK (2xx), repeticiones razonables con backoff + jitter, idempotencia y deduplicación rigurosas, seguridad competente (HMAC/mTLS), colas + DLQ + réplicas, y observabilidad transparente. Fije el contrato, introduzca límites y métricas, ejecute los escenarios de caos con regularidad y sus integraciones dejarán de «saltar» cuando se produzcan los primeros fallos.

Contact

Póngase en contacto

Escríbanos ante cualquier duda o necesidad de soporte.¡Siempre estamos listos para ayudarle!

Iniciar integración

El Email es obligatorio. Telegram o WhatsApp — opcionales.

Su nombre opcional
Email opcional
Asunto opcional
Mensaje opcional
Telegram opcional
@
Si indica Telegram, también le responderemos allí además del Email.
WhatsApp opcional
Formato: +código de país y número (por ejemplo, +34XXXXXXXXX).

Al hacer clic en el botón, usted acepta el tratamiento de sus datos.