Cómo hablan los servicios entre sí y con el daemon, de dónde salen los contratos y qué se genera de la tabla de rutas del bus.
Implementado. Los subjects concretos, sus versiones, topes y emisores están en la referencia generada del bus (
referencia/bus/, desdeBUS_ROUTES). Esta página explica el mecanismo.
La comunicación entre servicios usa NATS JetStream como bus (dec-0005) con tres familias de
subject:
| Familia | Forma | Semántica |
|---|---|---|
cmd | cmd.dominio.accion | Orden: pide un cambio y espera confirmación |
qry | qry.dominio.consulta | Consulta: respuesta sin efectos |
evt | evt.dominio.evento | Hecho ocurrido: sin respuesta |
Los bytes de vídeo nunca viajan por el bus. Lo que sí cruza es control: abrir una sesión en el
daemon (cmd.media.createSession), pedir los hechos de un fichero (qry.media.probe), dar de
alta lo ingerido (cmd.catalog.registerIngested) o publicar señales de transporte
(evt.media.transportSignals).
Cada mensaje es un contrato definido en @styx/api-contracts (src/bus/): subject, familia,
versión, tope de bytes y los esquemas JSON (TypeBox 1.x) de petición y de respuesta. Los contratos
se definen una sola vez y de ahí salen:
@styx/api-contracts es la fuente canónica contract-first (dec-0116): no se deriva de los tipos
de Elysia y no importa elysia.
BUS_ROUTES: la tabla única de autorizaciónBUS_ROUTES (packages/api-contracts/src/bus/routes.ts) declara, para cada subject:
nats o unix, este último es el
socket de control del daemon);allow), por identidad de servicio;El criterio de la lista de emisores es deliberado: nombra a quien hoy llama al handler en un
camino de producción. Un handler sin emisor de servicio sólo admite styx-ops (herramientas de
operación y tests, con identidad propia fuera del llavero de producción). No hay consumidores
previstos.
Las identidades del bus son catalog-svc, identity-svc, media-daemon, playback-svc,
realtime-svc, sources-svc, workers-svc, styx-ops y la web.
bun run gen:bus # escribe
bun run check:bus # falla si lo versionado difiere de lo generadoDe BUS_ROUTES salen tres cosas, y ninguna se edita a mano:
busHandler la toma de la
tabla. Un handler sin policy hace que el servicio no arranque.native/zig/media-daemon/ipc/contracts.generated.zig): structs
con validación y las policies del socket de control. Sin policy no compila.deploy/nats/nats-authorization.conf): un usuario por servicio que publica
exactamente lo que alguna lista de emisores le permite y suscribe sus handlers y su buzón. Un
servicio sin subjects de publicación recibe deny explícito. Las cuentas de servicio no pueden
crear ni cambiar streams de JetStream: los streams los provisiona el despliegue fuera de banda
(bun run bus:streams).Todo mensaje viaja en el sobre v2 de spire: identificador, subject y versión de contrato, identidad del emisor, el JWT del usuario en cuyo nombre se actúa (si aplica), marca temporal y nonce anti-replay, plazo, ids de correlación y traza, y una firma Ed25519 sobre la cabecera y el digest del payload. La seguridad de ese sobre se explica en comunicaciones entre procesos.
Nada habla NATS ni el socket de control por su cuenta. @styx/bus es el único punto de los
servicios que importa los transportes de spire, y un test de arquitectura falla si cualquier
fichero de apps/, packages/ o tools/ importa nats, o si alguien fuera de @styx/bus
importa los transportes. En Zig, la auditoría de seguridad prohíbe sockets sin pasar por el
transporte de spire. Así mover un handler de dentro a fuera de proceso no cambia su semántica ni
abre un hueco.