Skip to main content
The Smithers UI surface is React. This package is its SDK: a provider holding one SmithersGatewayClient, live data hooks that read a run (or runs, approvals, crons, scores, …) over TanStack DB collections, and action hooks that launch, approve, and cancel. Most hooks share the GatewayAsyncState shape, so knowing one means knowing them all.
Everything here lives at the subpath smthrs/gateway-react, not the bare smthrs facade. Import from the subpath, or the build fails.
For a UI served by the gateway itself, skip the JSX provider and mount with createGatewayReactRoot instead: it wires both contexts (on-demand hooks and the live collections) in one call.

GatewayAsyncState

The return shape shared by the live data hooks; see field detail below.
object
Source GatewayAsyncState.ts · See also Custom workflow UI

Provider & root

SmithersGatewayProvider

Holds one SmithersGatewayClient in context for every hook below. Pass a ready client, or options to construct one. The client is memoized on the content of options, so an inline literal won’t trigger a reconnect storm while a rotated credential or transport still rebuilds the client. Clients the provider builds are the provider’s to dispose: it closes the previous one when options rotate it in, and closes both the client and the collection data client on unmount, so no abandoned socket or reconnect timer survives the tree. A client passed as the client prop is never closed.
SmithersGatewayClient
A pre-built client. Takes precedence over options. See the Gateway Client reference.
SmithersGatewayClientOptions
Client config (baseUrl, token, …) used to construct a client when none is passed.
WorkspaceMode
Optional local or multiplayer collection mode. When omitted, local mode uses the client’s base URL.
ReactNode
The provider mounts both the raw SmithersGatewayClient context and the TanStack DB collection provider, so every live and action hook below works inside this one provider.
Source SmithersGatewayProvider.ts · Tests SmithersGatewayProvider.test.ts

createGatewayReactRoot

Mounts a full custom UI in one call: builds a client, mounts SmithersGatewayProvider, creates the TanStack DB collection registry, and renders your element. This is what a gateway-served ui entry uses.
ReactElement
required
The app root to render.
SmithersGatewayClientOptions & { rootId?: string }
Client options plus rootId (the DOM element id to mount into; default "root") and optional mode. Throws if the element is not found.
object
The client it created, for imperative use outside React.
Source createGatewayReactRoot.ts · See also Custom UI

useSmithersGateway

Reads the raw SmithersGatewayClient from context, throwing if called outside a provider: the escape hatch for client methods the hooks don’t wrap.
Source useSmithersGateway.ts · See also Gateway Client

SmithersCollectionsProvider

Advanced provider for supplying a custom WorkspaceMode, SmithersDataClient, or QueryClient. Most apps get this automatically from SmithersGatewayProvider.
WorkspaceMode
Local mode uses the Gateway REST API and SSE invalidation. Multiplayer mode uses Electric shapes for reads and the domain API for writes.
SmithersDataClient
Pre-built data client. Takes precedence over mode.
QueryClient
TanStack Query client. A default client is created when omitted.
Source SmithersCollectionsProvider.ts

useSmithersCollections

Read the TanStack DB collection registry and data client from context. Use this for custom useLiveQuery reads.
Source useSmithersCollections.ts · See also Sync

useGatewayConnectionStatus

The link’s connection lifecycle, derived from real transport traffic: RPC resolves and stream frames mark it online, transport errors mark it offline, auth failures mark it unauthorized.
"idle" | "connecting" | "online" | "offline" | "unauthorized"
Current connection state.
boolean
Shorthand for status === "online".
number
Epoch ms of the first failure in the current offline streak, when offline.
Source useGatewayConnectionStatus.ts · Tests sync.test.ts

Data hooks

Each hook reads one gateway resource as a live TanStack DB collection, sharing the GatewayAsyncState return shape unless noted. All may be called unconditionally: pass undefined (or an empty runId) and the hook resolves to an empty, stable state.

useGatewayRun

Live single-run record. Seeds from getRun, then each lifecycle frame upserts the row without a whole-tree refetch.
string | undefined
required
The run to read. undefined yields an empty state.
object
See GatewayAsyncState. data is the run record.
Source useGatewayRun.ts · Tests gateway-react.test.ts

useGatewayRunEvents

Live, bounded run-event buffer (resilient stream with afterSeq resume). Heartbeats are surfaced separately and never enter events; the array is capped to maxEvents, most-recent wins. Returns its own shape, not GatewayAsyncState. Frames reconstructed from persisted rows carry an optional timestampMs (epoch millis from the stored row) so log UIs can render when an event happened without a second lookup; those frames surface stateVersion: 0.
string | undefined
required
number
Drop events at or before this sequence number.
number
default:"1000"
Cap on the retained event buffer.
Array<GatewayEventFrame & { timestampMs?: number }>
Ordered, capped run events (heartbeats excluded). timestampMs is set on frames reconstructed from persisted rows.
(GatewayEventFrame & { timestampMs?: number }) | undefined
The most recent heartbeat frame, surfaced apart from events.
Error | undefined
Set when the stream fails (offline / unauthorized).
boolean
True while the stream is live.
Source useGatewayRunEvents.ts · See also Event types

useGatewayRuns

Live run list. Seeds from listRuns, re-pulls on invalidate.
ListRunsRequest
Optional filters (status, workflow, paging). Defaults to all runs.
object
See GatewayAsyncState. data is the run summaries.
Source useGatewayRuns.ts · Tests gateway-react.test.ts

useGatewayWorkflows

Live registered-workflow list (listWorkflows).
ListWorkflowsRequest
Optional filter.
object
Source useGatewayWorkflows.ts

useGatewayApprovals

Live pending-approval list (listApprovals). Re-pulls when a run reaches waiting-approval or after a submitApproval.
ListApprovalsRequest
Optional filters, e.g. { filter: { runId } } to scope to one run.
object
See GatewayAsyncState. data IS the array of pending gates (ListApprovalsResponse = GatewayApprovalSummary[]); there is no data.approvals wrapper. Each gate is { runId, nodeId, iteration, requestTitle?, requestSummary?, workflowKey?, requestedAtMs } (the title is requestTitle, not title). Pass nodeId + iteration straight into submitApproval.
Source useGatewayApprovals.ts · See also useGatewayActions

useGatewayCrons

Live cron-schedule list (cronList). Includes enabled and disabled rows; re-pulls after a cronCreate / cronDelete / cronRun.
CronListRequest
object
Source useGatewayCrons.ts

useGatewayMemoryFacts

Live cross-run memory facts (listMemoryFacts). Pass a namespace to scope; omit it for every namespace. Read-only on the wire, so query-only.
string
Optional namespace filter.
object
See GatewayAsyncState. refetch works; there is no write RPC.
Source useGatewayMemoryFacts.ts

useGatewayNodeOutput

On-demand output of one node (getNodeOutput). Built on useGatewayRpc; disabled until both ids are set.
string | undefined
required
string | undefined
required
number
default:"0"
Loop iteration to read. Pass 0 for a normal (non-looping) task.
object
See GatewayAsyncState. data is a { status: "produced" | "pending" | "failed", row, schema, partial? } envelope; the task’s output object is under data.row, not data itself. Destructure defensively (some code paths hand you the row directly), the way .smithers/ui/vcs.tsx does:
Source useGatewayNodeOutput.ts

useGatewayScores

Live scorer/eval results for one run (listScores). Pass nodeId to scope one node; an empty runId resolves to a stable empty collection. Read-only, so query-only.
string
required
The run to score. Empty string yields an empty state.
string
Optional node scope.
object
Source useGatewayScores.ts

useGatewayTickets

Live work docs (tickets, plans, specs, proposals) via listTickets. Tombstones are filtered server-side, so every row is renderable. Pass a kind to scope.
ListTicketsRequest
Optional kind and other filters.
object
Source useGatewayTickets.ts

useGatewayPrompts

Live registered-prompt list (listPrompts, walked from .smithers/prompts/). Read-only on the wire, so query-only; takes no arguments.
object
Source useGatewayPrompts.ts

useGatewayRpc

The generic escape hatch: call any gateway RPC by name and get its typed payload back in GatewayAsyncState. The typed hooks above wrap this; reach for it when none exists. Disable with enabled: false (a disabled or key-changed query clears stale data instead of surfacing it).
GatewayRpcMethod
required
The RPC method name.
GatewayRpcParams<Method>
required
Typed params for that method.
boolean
default:"true"
Skip the request when false.
readonly unknown[]
Re-fetch trigger. Defaults to the serialized params.
object
Source useGatewayRpc.ts · See also Gateway Client

useDelegationChain

Folded delegation-chain state for one run: the read model behind the delegation-chain workflow UI. Enumerates every physical dc:* node from the live run tree, fetches each node’s durable output row once (re-checked on finish or failure), folds the rows through the pure foldDelegation reducer, and returns the graph plus delegation actions. Malformed or unknown rows surface in errors instead of throwing.
string | undefined
required
The run to fold. undefined (or an empty string) yields an empty graph.
DelegationGraph
Nodes keyed by logical id (status, version history, gates, attention rollups), edges, the current phase, pending question forms, the refined prompt, the predicted-vs-actual budget rollup, and run scores.
boolean
True until the run tree and the first output sweep have hydrated.
unknown[]
Fold issues (ignored rows) plus any tree/event/output fetch errors.
object
The pure reducer is exported alongside it (foldDelegation, parseDelegationNodeId, delegationTableForNodeId) together with the DelegationGraph and Dc*Row types, for tests and non-React consumers. Source useDelegationChain.ts · See also <DelegationChain>

Action hooks

useGatewayActions

Bound, memoized mutation methods off the client: launch, resume, cancel, hijack, rewind, approve/deny, signal, and manage crons. Each takes the matching RPC params and returns a promise.
object
Source useGatewayActions.ts · See also Gateway Client

useGatewayMutation

Typed mutation helper for supported domain writes. It calls the same domain API as useGatewayActions, then invalidates the collection registry.
string
required
One of the supported domain mutations: launchRun, resumeRun, cancelRun, hijackRun, rewindRun, submitApproval, submitSignal, cronCreate, cronDelete, cronRun, createTicket, updateTicket, or deleteTicket.
readonly unknown[]
Reserved for compatibility. Successful mutations invalidate the collection registry.
object
{ mutate, mutateSafe, isLoading, error }.
Source useGatewayMutation.ts · See also useGatewayActions

Type exports

These types are exported from the same subpath for typing your own components.
type
The shared data-hook return shape. See above.
type
{ client, collections, queryClient } from useSmithersCollections.
type
Connection state used by useGatewayConnectionStatus.
Source index.ts · Tests gateway-react.test.ts
This is the UI side of the control plane. For the underlying transport and its imperative methods, see the Gateway Client reference. To embed a UI in a gateway-served workflow, see Custom UI and the Custom workflow UI guide.