Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

12 — API Mapping (WS / Realtime Module)

Honest statement: the ws module exposes NO REST endpoints. It is a socket contract only. General API conventions live in 00-shared/07; this file maps the socket contract 1:1 to source, and marks every gap explicitly.


1. REST surface: none

MethodPathStatus
No HTTP endpoints. The module consists of gateway + bridge only (ws.module.ts:6-9). Auth is via JWT on the socket handshake, not via any REST call of this module.

2. Transport & handshake

AspectContractSource
Endpointws(s)://<host>/ws (socket.io namespace /ws)ws.gateway.ts:20-23
AuthBearer-style access token in handshake.auth.token or handshake.query.tokenws.gateway.ts:37-39
VerificationJwtService.verify with JWT_ACCESS_SECRET; payload {sub, tenantId, roles}ws.gateway.ts:42-48
Failuresocket disconnected, no error framews.gateway.ts:54-56
CORSorigin: '*', credentials truews.gateway.ts:22

3. Client → Server events (the only wire inputs)

EventPayloadEffectSource
subscriberoom: string (any)join room; future broadcastToRoom deliveriesws.gateway.ts:63-68,80-82
unsubscriberoom: string (any)leave roomws.gateway.ts:70-74

No other client messages are handled; unknown events are ignored. No acks, no errors.

4. Server → Client events

Event namePayload envelopeDeliverySource
{eventType} — any domain event type, dot-notation (API_STANDARDS.md:642-658), e.g. notification.created, payment.completed, attendance.updated, homework.published{ eventType: string, occurredAt: ISO-8601, payload: object }tenant:{tenantId} room — all connected sockets of the tenantws-bridge.service.ts:16-22; ws.gateway.ts:76-78

Details:

  • The bridge relays every EventBus event (events/event-bus.service.ts:11-14) for the event's tenant — there is no server-side allow-list of event types.
  • The envelope is a subset of DomainEvent (events/domain-event.interface.ts:1-8): actorId and correlationId are dropped by the bridge (ws-bridge.service.ts:17-21) — gap G3.
  • broadcastToRoom(room, event, data) exists (ws.gateway.ts:80-82) and is used for ad-hoc room fan-out, but nothing in source calls it today.

5. Known gaps (all verified in source)

#GapEvidenceImpact / recommendation
G1No ws.* permissions in RBACALL_PERMISSIONS (permissions.constants.ts:1-97) contains no ws.* entriesAdmin debug view has no permission gate; add ws.monitor when debug surfaces ship
G2subscribe accepts any room string, no allow-list/RBACws.gateway.ts:65,71Any authenticated user can join room X if another module broadcasts there; enforce room-prefix allow-list + permission check
G3Bridge drops actorId/correlationIdws-bridge.service.ts:17-21 vs domain-event.interface.ts:4-6Client dedup uses entityId heuristics; forward correlationId
G4No per-user room / private deliveryrooms = tenant + ad-hoc (ws.gateway.ts:50,63-68)Sensitive notifications must define user:{id} convention + RBAC
G5No Redis pub/sub adapter for socketssrc/infrastructure/redis/ has only REDIS_CLIENT (redis.constants.ts:1-2, redis.module.ts:12-27); no socket.io adapter in srcMulti-instance deployments will fan out only within one process; add socket.io Redis adapter when scaling (plan flags 10k-connection risk, IMPLEMENTATION_PLAN.md:842)
G6No heartbeat tuning in sourcegateway sets no pingInterval/pingTimeoutRelies on socket.io defaults (25 s / 20 s); tune for proxy timeouts
G7No server-side event allow-list / per-event subscriptionbridge relays everything (ws-bridge.service.ts:16-22)Clients filter client-side; adds bandwidth; plan per-eventType subscription
G8roles unusedset at connect (ws.gateway.ts:48) but never read for routingfuture per-role delivery; do not rely on it today

6. Planned socket consumers

ConsumerContractStatus
Communication (messages)realtime delivery via WsModuleplanned — docs/IMPLEMENTATION_PLAN.md:119
Async job progressclients subscribe via WS instead of polling (API_STANDARDS.md:579)planned
Transport live trackingtransport.* eventsplanned — docs/IMPLEMENTATION_PLAN.md:229
Notificationspush + in-app channelsplanned — docs/IMPLEMENTATION_PLAN.md:231

7. Versioning & errors

  • No versioning (no REST). Event names follow dot-notation and are additive; clients must ignore unknown eventTypes (06 §6).
  • Error signalling is connection-level only (disconnect on auth failure, ws.gateway.ts:54-56). No application error channel — add one for G-series fixes.