Something went wrong. Try again.
Something went wrong. Try again.
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879/** * Lifecycle events — PROTOCOL §9.1. * * `hello` (first on connect), `sync` (after agent.attach / on reconnect), `status` * (agent status changes). All are server→client events and never carry a correlation `id` * (§5.1). Reuses AgentStatus, Message, PermissionRequest, UiRequest — no duplication. */import { Type, type Static } from '@sinclair/typebox';import { AgentStatusSchema } from '@/contracts/agent-info';import { MessageSchema } from '@/types/message';import { PermissionRequestSchema, UiRequestSchema,} from '@/contracts/event';
/** The protocol version carried by `hello` (single source of truth, §7). */export const PROTOCOL_VERSION = '0.1.0';
/** `hello` — emitted immediately on connect (§9.1). Client checks the version (§7). */export const HelloSchema = Type.Object({ type: Type.Literal('hello'), protocol_version: Type.Literal(PROTOCOL_VERSION), server_version: Type.String(), capabilities: Type.Array(Type.String()),});
/** `sync` — agent bootstrap state, sent after `agent.attach` or direct `hello` (§9.1, §6.4). */export const SyncSchema = Type.Object({ type: Type.Literal('sync'), /** Present on daemon connections; direct connections have one implicit agent (§5.2). */ agent_id: Type.Optional(Type.String()), status: AgentStatusSchema, /** The agent's authoritative active mode at the time of the snapshot. */ mode: Type.String(), /** * The attached runtime's secret-free capabilities (saga vr7kgx.6). Current servers always * emit it; optionality lets an older/malformed runtime degrade to no controls rather than * forcing the browser to infer support from the protocol version (§7). Projected from the * child runtime's `hello.capabilities` by the daemon; on a direct connection it mirrors the * child's own hello. The top-level daemon `hello` remains transport-scoped and does NOT * advertise per-runtime model support globally. */ capabilities: Type.Optional(Type.Array(Type.String())), /** * The attached runtime's authoritative generation epoch (saga vr7kgx.6 hardening). The * daemon increments it on every same-`agent_id` child-runtime replacement and includes * it in every daemon-authored `sync` (attach + post-replacement re-sync). A browser uses * it to fence stale catalogs/responses emitted by a superseded generation so an old * stream's late events cannot mutate current-generation state. Optional + additive: an * older/direct-connection `sync` omits it and a client treats absence as a stable * baseline (no fencing needed on a single-generation direct connection). */ runtime_epoch: Type.Optional(Type.Integer({ minimum: 0 })), live_window: Type.Object({ messages: Type.Array(MessageSchema), compaction_index: Type.Optional(Type.Integer()), }), pending_requests: Type.Array(Type.Union([PermissionRequestSchema, UiRequestSchema])),});
/** `status` — agent status change (§9.1). */export const StatusEventSchema = Type.Object({ type: Type.Literal('status'), agent_id: Type.Optional(Type.String()), status: AgentStatusSchema, detail: Type.Optional(Type.String()),});
export const LifecycleEventSchema = Type.Union([ HelloSchema, SyncSchema, StatusEventSchema,]);
export type Hello = Static<typeof HelloSchema>;export type Sync = Static<typeof SyncSchema>;export type StatusEvent = Static<typeof StatusEventSchema>;export type LifecycleEvent = Static<typeof LifecycleEventSchema>;