APIWebSocket Events

WebSocket Events

BioNodulo has no public run-progress WebSocket API. Live updates use two real mechanisms, documented here:

  • Run progress — Server-Sent Events (SSE) over plain HTTP, plus polling fallbacks. SSE works through every proxy and survives serverless constraints; the Next.js App Router cannot host a raw WebSocket route without a custom server, so SSE is the primary transport.
  • Editor collaboration — a WebSocket, but an internal one: the editor’s Yjs document sync runs on a dedicated Cloudflare Worker (collab.bionodulo.com), authenticated by per-room tokens. It is not a general-purpose event stream.

Run progress over SSE

GET /api/runs/{runId}/stream
Authorization: Bearer $BIONODULO_SESSION_TOKEN   # or same-origin session cookie

Response: text/event-stream. Each data: line is one JSON envelope.

Message shapes

TypeFieldsMeaning
connectedrunIdStream is open
snapshotrunId, status, logs, durationMs, creditsUsed, errorMessage, outputLocationCurrent DB state, sent immediately on connect so late joiners see the latest
(progress)status, progressPercent, nodeId, nodeName, currentStep, logs, resources, …Live worker updates, relayed as they arrive
donerunId, statusTerminal state reached; the server closes the stream

Notes:

  • If the run is already in a terminal state (completed, failed, cancelled, interrupted) you get connectedsnapshotdone and a clean close.
  • A : heartbeat comment is sent every 25 s to keep intermediaries from closing an idle connection.
  • The stream is backed by Redis pub/sub in production; progress is also persisted to the run row, so nothing is lost if you disconnect.

Polling fallbacks

For environments where SSE is awkward, two poll endpoints cover the same state:

  • GET /api/runs/{runId} — the full snapshot (status, logs, creditsUsed, durationMs, …). This is what the cloud editor itself polls.
  • GET /api/runs/{runId}/events?after_seq=N&limit=K — the durable, curated run-event log (node retries, errors, queue transitions, terminal changes), ordered by a monotonic seq. Pass the last seq you saw as after_seq to resume after a gap without re-reading; limit defaults to 100, max 500.

Editor collaboration WebSocket (internal)

The collaborative editor syncs the canvas with Yjs over WebSocket:

wss://collab.bionodulo.com/editor/{room}?token={roomToken}
  • room is {teamId}_{workflowId}; the token is a short-lived (1 h) HMAC-signed room token minted by POST /api/collab/token (team members) or returned by POST /api/collab/join (share-link guests).
  • The Worker verifies the token and the request Origin before upgrading the socket, then routes it to a per-room Durable Object.

This channel carries Yjs document updates, not run events — use the SSE stream above for execution progress.

Reconnection

If a stream drops, reconnect: the server replays the current snapshot on connect. For the durable event log, reconnect with after_seq set to the last received seq. Combine with a GET /api/runs/{runId} poll to re-sync full state.

See also