Skip to content

Protocol overview

The following diagram shows the typical happy-path message flow across both WebSocket layers, from connection setup through webhook relay to job completion.

These messages are shared across both WebSocket layers.

Authoritative source: packages/engine/src/protocol/messages/common.ts

Sent periodically to keep the WebSocket connection alive. Both orchestrators (to Platform) and agents (to orchestrators) send heartbeats on a 30-second interval.

FieldTypeRequiredDescription
type"heartbeat"YesMessage discriminator
timestampnumberYesUnix timestamp (milliseconds)

Authoritative source: packages/engine/src/protocol/messages/common.tsheartbeatSchema

Positive acknowledgment of a received message. Used for generic message-level acknowledgments.

FieldTypeRequiredDescription
type"ack"YesMessage discriminator
messageIdstringYesID of the message being acknowledged

Authoritative source: packages/engine/src/protocol/messages/common.tsackSchema

Negative acknowledgment — the message was received but could not be processed.

FieldTypeRequiredDescription
type"nack"YesMessage discriminator
messageIdstringYesID of the message being rejected
reasonstringYesHuman-readable rejection reason

Authoritative source: packages/engine/src/protocol/messages/common.tsnackSchema

Protocol-level error notification. Sent when something goes wrong at the connection level.

FieldTypeRequiredDescription
type"error"YesMessage discriminator
codestringYesError code identifier
messagestringYesHuman-readable error message

Authoritative source: packages/engine/src/protocol/messages/common.tserrorSchema

Used during WebSocket connection establishment. The connecting party sends auth.request and the server responds with either auth.success or auth.failure.

Authoritative source: packages/engine/src/protocol/messages/auth.ts

Sent by the connecting party (orchestrator to Platform, or agent to orchestrator) to authenticate.

FieldTypeRequiredDescription
type"auth.request"YesMessage discriminator
tokenstringYesAPI key or authentication token
protocolVersionnumber (int > 0)YesProtocol version (currently 1)
capabilitiesOrchCapabilitiesNoOrchestrator capabilities (optional for backward compat with pre-capability orchestrators)

OrchCapabilities fields:

FieldTypeRequiredDescription
orchRole"coordinator" | "worker"NoOrchestrator’s role in the cluster (coordinator manages DB/vault, worker is stateless)
dashboardWritesRecord<string, boolean>NoSparse per-operation dashboard-write policy map. Each present key flips one DashboardWriteOperation to false; missing keys default to true (permissive). Sent on auth so the upstream cache populates immediately; rebroadcast via orch.capabilities.update on change

The schema uses .passthrough() so newer orchestrators can send additional flags without breaking older upstream versions. Unknown flags are preserved.

Authoritative source: packages/engine/src/protocol/messages/auth.tsauthRequestSchema

Sent by the server after successful authentication.

FieldTypeRequiredDescription
type"auth.success"YesMessage discriminator
connectionIdstringYesUnique connection ID assigned by server
orgPublicAliasstringNoPublic alias (oal_<12-char>) of the authenticated orchestrator’s owning org. Used by the orchestrator’s check-run emitter to build a details_url that points at the dashboard’s resolver route, so the canonical org_<12-char> id never appears in public surfaces

Authoritative source: packages/engine/src/protocol/messages/auth.tsauthSuccessSchema

Sent by the server when authentication fails. The WebSocket connection is closed immediately after this message.

FieldTypeRequiredDescription
type"auth.failure"YesMessage discriminator
reasonstringYesHuman-readable failure reason

Authoritative source: packages/engine/src/protocol/messages/auth.tsauthFailureSchema