Espécimen arquitectónico de I+D 02 — Referencia: capa de integración empresarial
Cola de eventos tolerante a fallos: aceptación duradera, reintentos acotados, efecto idempotente
Espécimen arquitectónico de I+D: investigación y desarrollo del estudio, construido y medido en este repositorio. No es un trabajo de cliente y no describe a ningún cliente. Cada cifra de esta página está medida o calculada, y se indica su método.
Pregunta de diseño
Cuando un sistema de una cadena se detiene, los eventos no deben desaparecer ni aplicarse dos veces. ¿Puede una pequeña máquina de estados sin dependencias dar entrega al menos una vez con efecto como máximo una vez, sobrevivir a un reinicio y a un canal muerto, y demostrarlo en escenarios de fallo deterministas?
Nivel de evidencia B: una implementación de referencia verificada por pruebas ejecutables. No está conectada a los sistemas de ningún cliente; los volúmenes, las credenciales y el contexto legal quedan fuera de lo que afirma este espécimen.
I
Restricción y tolerancia
Tres modos de fallo, cada uno con una tolerancia escrita.
Pérdida: un evento confirmado a su productor debe sobrevivir a un reinicio y a un canal muerto. La aceptación es una escritura duradera que ocurre antes de la confirmación.
Repetición: las redes repiten. La entrega es al menos una vez, así que el receptor aplica un identificador de evento una vez y descarta la repetición, quienquiera que lo reenvíe.
Falta de límite: ningún evento puede reintentarse sin fin ni retenerse sin fin. Los intentos, la antigüedad y el resultado en cada límite (a las cartas muertas, conservado, nunca descartado) están escritos como política.
II
Arquitectura
Una máquina de estados sin temporizadores y sin entrada ni salida propias.
El llamador aporta el reloj, el almacén duradero y el canal, de modo que el mismo código se ejecuta en una simulación determinista, en el navegador y, con un almacén y un canal reales, en un proyecto.
Estados: pendiente, reintento, aparcado, entregado, muerto. Los envíos fallidos se reintentan con retroceso exponencial. Tras una racha de fallos y una sonda de salud fallida el circuito se abre: los eventos se aparcan en el almacén y una sonda barata prueba el canal hasta que vuelve; entonces el atrasado se vacía en orden.
Aislamiento de eventos venenosos: un evento que falla en un canal sano es un mal evento, no un canal muerto. Se reintenta dentro de su presupuesto, luego pasa a las cartas muertas y el circuito sigue cerrado; así un mal evento no detiene la cola que tiene detrás más allá de ese presupuesto.
III
Verificación
Escenarios deterministas y un conjunto fijo de invariantes.
Entre los escenarios figuran un canal caído veinte segundos, un canal intermitente, confirmaciones perdidas en el 30 % de los envíos, un evento venenoso, un evento obstinado, reinicios durante una caída, un productor que envía dos veces y todo a la vez. Cada uno usa un reloj virtual y un generador con semilla: sin temporizadores, sin red.
En cada escenario las pruebas de contrato afirman que ningún evento aceptado se pierde, ninguno se aplica dos veces, se conserva el orden de aceptación y ningún evento se envía más veces de las que permite la política.
La tabla de resultados de la documentación se genera a partir del código y una prueba la compara con él, de modo que la evidencia es lo que el código hace hoy.
Dónde se aplican los niveles: esta cola es de nivel de evidencia B (una referencia verificada por pruebas). El webhook firmado con entrega idempotente que este sitio ejecuta en producción es de nivel A.
IV
Resultado medido y límites
Calculado a partir del código que ejecutan las pruebas.
Medido
Estas cifras se calculan al dibujar la página, ejecutando los escenarios que ejecutan las pruebas de contrato. Son deterministas: iguales en cada solicitud.
- Escenarios ejecutados
- 9
- 9 de 9 mantuvieron todos los invariantes
- Eventos aceptados
- 370
- en todos los escenarios
- Eventos perdidos
- 0
- cada evento aceptado aplicado, en las cartas muertas o aún en cola
- Eventos aplicados dos veces
- 0
- se descartaron 56 repeticiones
Calculado a partir de lib/arch/scenarios.ts con el simulador que ejecutan las pruebas de contrato, al dibujar esta página. 5 eventos pasaron a las cartas muertas (conservados, nunca descartados): eventos venenosos u obstinados, por diseño.
Compromisos y límites
Lo que cuesta este patrón y dónde necesita al cliente.
Al menos una vez significa repeticiones
Las repeticiones ocurren por diseño, así que el receptor debe poder con ellas y recordar los identificadores más tiempo que el máximo que la cola puede seguir reintentando.
El orden cuesta disponibilidad
Con orden estricto, un evento que falla retrasa a los que le siguen hasta que tiene éxito o pasa a las cartas muertas. Desactívelo para eventos independientes.
El almacén es una dependencia
La durabilidad es tan fuerte como el almacén que se da a la cola. Su elección (una base de datos, una cola gestionada) y sus propias garantías corresponden al proyecto.
Medido en
- TypeScript · no dependencies
- Virtual clock · seeded generator
- Node · browser