Skip to main content

Installation

Initialization

RegisterWorker

RegisterWorker creates a Client for the engine at url and starts the connection lifecycle in the background, returning immediately. An empty url means EngineURLFromEnv, as with New. It is the idiomatic entry point, matching registerWorker in the Node SDK and register_worker in the Rust SDK. Register functions and triggers on the returned client; they are (re)sent on each connection. Call Client.Close to stop. To wait for the first connection (or fail fast on a bad URL), call Client.Connect instead of (or after) RegisterWorker; it blocks until connected, ctx is done, or the reconnect budget is exhausted. Use New if you want to build a client without starting the connection. Signature
string
required
...Option

Methods

Client.RegisterTrigger

Deprecated. Use Client.Observe instead: client.Observe(iii.Source{FunctionID: “orders::create”}, functionID) for the invocations of a function, or iii.Source{FunctionID: iii.FnOnWorkersChanged, Deliver: iii.DeliverInput} for an engine-hosted source. Built-in trigger providers (http, cron, queue, …) keep RegisterTrigger until they ship their source functions. Migration guide: https://iii.dev/docs/upgrading/from-0-24-x
RegisterTrigger registers a trigger instance described by input, fire input.FunctionID when a trigger of input.Type matches input.Config, and returns its handle; Trigger.Unregister removes it. An empty input.ID makes the SDK generate one (a random UUID), nil Config is sent as {}, an empty Namespace means this worker’s namespace and an empty TriggerNamespace lets the engine resolve the type’s provider. Config and Metadata must be valid JSON. The registration is kept in memory and sent again on every reconnect; registering the same ID again replaces it. It mirrors registerTrigger in the Node SDK. It keeps working (through a live trigger-type provider or the engine’s legacy shim), and logs a deprecation warning once per process. Signature

Parameters

RegisterTriggerInput
required

Client.RegisterFunction

RegisterFunction registers a function this worker can handle and returns its handle; FunctionRef.Unregister removes it. It may be called before or after Connect; the registration is sent on the next (re)connect. As in the Node, Python and Rust SDKs, an empty id is refused (“id is required”) and so is an id this client already registered (“function id already registered”): to replace a function, unregister it first. Pass a single RegisterFunctionOptions value for a description, request and response formats, metadata, observe hooks or the local dispatch setting. Handlers read the optional per-invocation metadata sidecar from their ctx with MetadataFromContext. Signature
string
required
Handler
required
...RegisterFunctionOptions

Client.Trigger

Trigger invokes a function on the engine. With the default (nil) or an enqueue action it waits for the matching invocation result and returns it, mapping a remote error to InvocationError and a missed deadline to ErrTimeout. With a VoidAction it is fire-and-forget and returns immediately with a nil result. ctx bounds the wait independently of TriggerRequest.Timeout: if ctx is cancelled first, its error is returned and the pending entry is reclaimed. Inside a handler, pass the handler’s ctx: the call then carries the handler as its caller (and the observe depth), which observers’ filters and the engine’s loop guard read. A function this worker hosts runs in-process, without touching the wire, once the engine confirmed it for local dispatch, unless the action is enqueue or Dispatch is DispatchRemote. The handler gets its own copy of the payload and the caller a fresh encoding of the result; errors and timeouts look as on the remote path. Observers of a local call see the payload and metadata as they were when the call started (snapshots), whatever the caller or the handler does with them afterwards. The handler runs on a goroutine of its own, so the caller always returns on its Timeout or ctx deadline, even when the handler blocks and ignores its ctx; the handler then runs to completion (as a remote one would on its worker), its result is discarded, and the call is still counted and reported to observers. A handler that can block for long should honor its ctx (cancelled on Close), or opt out with RegisterFunctionOptions.LocalDispatch. Signature
context.Context
required
TriggerRequest
required

Client.RegisterTriggerType

Deprecated. Register a function with an observe descriptor instead: RegisterFunction(id, handler, iii.RegisterFunctionOptions{Observe: &iii.ObserveHooks{ Delivery: iii.DeliveryOwner, OnObserverAdded: …, OnObserverRemoved: …}}). Its observers are what trigger instances were. Migration guide: https://iii.dev/docs/upgrading/from-0-24-x
RegisterTriggerType registers a custom trigger type (for example “webhook”) with the handler the engine calls to start and stop individual trigger instances of it, and returns its handle: TriggerTypeRef.RegisterTrigger and TriggerTypeRef.RegisterFunction bind triggers of the type, and TriggerTypeRef.Unregister removes it. Nonempty schemas in input must contain valid JSON; JSON Schema semantics are not checked. The SDK copies the schema bytes and resends them on reconnect. Registering the same id again replaces the registration; an invalid registration leaves an existing one unchanged. It keeps working, and logs a deprecation warning once per process. Signature

Parameters

RegisterTriggerTypeInput
required
TriggerHandler
required

Client.UnregisterTriggerType

Deprecated. Trigger types are replaced by functions with an observe descriptor; unregister the function with FunctionRef.Unregister instead. Migration guide: https://iii.dev/docs/upgrading/from-0-24-x
UnregisterTriggerType removes the trigger type registered under id with Client.RegisterTriggerType, as TriggerTypeRef.Unregister does: the engine retires it (when this connection provides it), and a reconnect does not register it again. It mirrors the Node SDK’s unregisterTriggerType. It returns an error when no trigger type with id is registered. Signature

Parameters

string
required

Client.Address

Address returns the engine WebSocket base URL this client dials (e.g. “ws://127.0.0.1:49134”): the url given to New or RegisterWorker, else EngineURLFromEnv. Channel readers/writers build their own URLs from it. Signature

Client.Close

Close shuts the client down at once: it stops the reconnect loop, gives buffered observe reports and telemetry a short, fixed time to go out (250ms for the reports, at most 10s for the telemetry flush), cancels all pending Trigger calls with ErrNotConnected, and drops the socket without a closing handshake. It does not send unregister frames (matching the reference SDKs). Use Client.Shutdown to wait for the flushes under a deadline of your own and close the socket gracefully. Close is idempotent and implements io.Closer; it always returns nil. Called while a Shutdown runs, it cuts that Shutdown short (as http.Server.Close does) and returns once it has finished. Signature

Client.Connect

Connect starts the connection lifecycle (if not already started) and blocks until the first connection is established, ctx is cancelled, or the reconnect budget is exhausted. The supervisor goroutine then keeps the connection alive (reconnecting with backoff) until Close. Connect is safe to call multiple times and from multiple goroutines; only one supervisor ever runs. Signature

Parameters

context.Context
required

Client.ConnectionState

ConnectionState returns the current state of the connection to the engine. It mirrors getConnectionState in the Node SDK; Client.OnConnectionStateChange reports every change. Signature

Client.CreateChannel

CreateChannel asks the engine to allocate a streaming channel and returns both ends. bufferSize bounds the engine’s internal queue; nil uses the engine default. Signature

Parameters

context.Context
required
*int
required

Client.FatalError

FatalError returns the terminal registration rejection that stopped this worker, or nil while healthy. Mirrors the Node/Python/Rust SDKs’ fatal-error accessors. Signature

Client.IsObserved

IsObserved reports whether functionID, registered by this worker, has active observers: one atomic load, for the emit fast path. Signature

Parameters

string
required

Client.LocalDispatchActive

LocalDispatchActive reports whether Trigger runs functionID in-process: it is registered here, the engine confirmed it with local_dispatch, and RegisterFunctionOptions.LocalDispatch did not opt out. Signature

Parameters

string
required

Client.Observe

Observe observes a function: every event of source (an invocation of an auto function, or what its owner hands over) that passes source.Filters invokes target, a function registered by some worker (until it is, the observer stays pending). It returns the handle at once, also before the connection is up; the observer is replayed with the same id on every reconnect. Errors from the engine (INVALID_ARGS, INVALID_FILTER, FORBIDDEN, SELF_TARGET, an owner’s rejection, and UNSUPPORTED against an engine without observe) show up as state error and fail ObserverHandle.Ready. The returned error is for a request that cannot be sent at all: a missing function or target, a reused id, a blank namespace, args or filters that are not JSON. Signature
Source
required
string
required
...ObserverOptions

Client.Observers

Observers returns the active observers of functionID, registered by this worker, as its owner sees them. Signature

Parameters

string
required

Client.OnConnectionStateChange

OnConnectionStateChange calls listener with the current ConnectionState, then with every later change of state (StateConnecting, StateConnected, StateReconnecting, StateDisconnected, StateFailed), in the order the changes happen. Calls are made one at a time on a goroutine of the client’s own, never on the subscribing goroutine or on the SDK’s read loop, so a listener may call any Client method; it should return promptly, since later changes wait for it. A state is reported once per change: the same state is never delivered twice in a row. A listener that panics is logged and keeps its subscription. It returns the function that unsubscribes listener: changes not yet delivered when it returns are dropped for this listener (a call already under way completes). Calling it more than once does nothing. It mirrors the Python SDK’s add_connection_state_listener. Signature

Parameters

func(ConnectionState)
required

Client.OpenReader

OpenReader returns a reader for the read end described by ref (typically received in a trigger payload), against this client’s engine address. Like the ends returned by Client.CreateChannel, its handshake sends the client’s WithHeaders plus “Authorization: Bearer $III_TOKEN” when that variable is set and the headers have no Authorization header. The socket connects on first read. Signature

Parameters

StreamChannelRef
required

Client.OpenWriter

OpenWriter returns a writer for the write end described by ref (typically received in a trigger payload), against this client’s engine address. Like the ends returned by Client.CreateChannel, its handshake sends the client’s WithHeaders plus “Authorization: Bearer $III_TOKEN” when that variable is set and the headers have no Authorization header. The socket connects on first send. Signature

Parameters

StreamChannelRef
required

Client.RegisterHTTPFunction

RegisterHTTPFunction registers a function that has no handler in this process: the engine invokes it by sending an HTTP request as described by invocation, which travels as the registration’s “invocation” field. invocation.URL is required; an empty Method means POST, as in the Node SDK. invocation.Auth, when set, must be valid JSON; build it with HMACAuth, BearerAuth or APIKeyAuth. Pass at most one RegisterFunctionOptions for the description, formats, metadata or observe hooks; LocalDispatch does not apply, since there is nothing to run in-process. Like every registration it is kept in memory and sent again on each reconnect. An empty id, or one this client already registered, is refused as in Client.RegisterFunction; FunctionRef.Unregister on the returned handle removes it. Signature

Parameters

string
required
HTTPInvocationRef
required
...RegisterFunctionOptions

Client.RegisterTriggerNamespaced

Deprecated. Use Client.Observe with ObserverOptions.TargetNamespace, or Client.RegisterTrigger with RegisterTriggerInput.Namespace for a built-in trigger provider. Migration guide: https://iii.dev/docs/upgrading/from-0-24-x
RegisterTriggerNamespaced registers a trigger with id that fires functionID, resolved in namespace (empty: this worker’s), when a trigger of triggerType matches config. It is Client.RegisterTrigger with the input spelled out, without the handle. It keeps working, and logs the RegisterTrigger deprecation warning once per process. Signature

Parameters

string
required
string
required
string
required
string
required
json.RawMessage
required
...json.RawMessage

Client.Shutdown

Shutdown shuts the client down gracefully, as the Node SDK’s shutdown does, bounded by ctx like http.Server.Shutdown: it stops the reconnect loop, waits until the buffered observe reports and counters are written, stops the worker gauges, flushes and stops the telemetry exporters, cancels all pending Trigger calls with ErrNotConnected, and closes the socket with a normal-closure handshake. When ctx is done before those steps finish, the remaining work is cut short (the socket is closed at once, also when the engine never answers the close handshake) and ctx.Err() is returned; the client is shut down either way and nil means everything was delivered. A Client.Close called meanwhile cuts it short the same way, and Shutdown then returns context.Canceled. Like Close it does not send unregister frames. Shutdown is idempotent: a later Shutdown returns once the first shutdown has finished, or ctx.Err() if its own ctx ends first. Signature
context.Context
required

Client.State

Deprecated. Use Client.ConnectionState.
State returns the current connection state. Signature

Client.WaitUntilRegistered

WaitUntilRegistered blocks until the engine has acknowledged this worker on the current connection, with the WorkerRegistered frame it sends on each connection, and then returns nil. While the client is disconnected it waits for the next connection’s acknowledgement. It returns the error of Client.FatalError when the worker was terminally rejected (for example a WORKER_NAMESPACE_CONFLICT, or a blank WithNamespace), and ctx.Err() when ctx is done first. Like the Rust SDK’s wait_until_registered, which it mirrors with ctx in place of a timeout, it returns ErrNotConnected when the client was never started (call it after Client.Connect or RegisterWorker), has been closed, or gave up reconnecting (ReconnectConfig.MaxRetries). Signature

Parameters

context.Context
required

Client.WorkerID

WorkerID returns the worker id the engine assigned with its last WorkerRegistered, or "" before the first one. The id is kept across a disconnect (the next connection presents it to reattach) until the engine assigns the next one. It mirrors worker_id in the Python SDK. Signature

Functions

APIKeyAuth

APIKeyAuth returns the HTTPInvocationRef.Auth that has the engine send an API key in the request header named header, the key being held in the engine’s environment variable valueKey: {“type”:“api_key”,“header”:header,“value_key”:valueKey}. Same shape as the api_key variant of the Node SDK’s HttpAuthConfig. Signature

Parameters

string
required
string
required

BearerAuth

BearerAuth returns the HTTPInvocationRef.Auth that has the engine send “Authorization: Bearer <token>”, the token being held in the engine’s environment variable tokenKey: {“type”:“bearer”,“token_key”:tokenKey}. Same shape as the bearer variant of the Node SDK’s HttpAuthConfig. Signature

Parameters

string
required

DefaultReconnectConfig

DefaultReconnectConfig is the reconnect schedule shared with the Node SDK: start at 1s, double each time, cap at 30s, ±30% jitter, retry forever. Signature

EngineURLFromEnv

EngineURLFromEnv returns the engine address a worker connects to when its code names none: the III_URL environment variable, trimmed, when it is not blank, else DefaultEngineURL. The supervisor that spawned the process (iii compose, a container runtime, systemd) sets III_URL the same way it sets III_NAMESPACE and III_WORKER_NAME. New and RegisterWorker call it when their url argument is empty, so an explicit address wins, then III_URL, then the default, as in the Node SDK. Signature

EnqueueAction

EnqueueAction routes an invocation through a named queue; the engine acknowledges with an enqueue receipt rather than the function’s result. Signature

Parameters

string
required

ExtractChannelRefs

ExtractChannelRefs recursively walks a JSON value and returns every StreamChannelRef found, keyed by its dotted path (e.g. “reader”, “data.writer”). A node is a ref iff it is an object with string channel_id, access_key, and direction fields. Mirrors extract_channel_refs and is_channel_ref in the Rust SDK: the receiving worker uses it to find a ref another worker embedded in a trigger payload. Signature

Parameters

json.RawMessage
required

HMACAuth

HMACAuth returns the HTTPInvocationRef.Auth that has the engine sign each request with HMAC, using the secret held in the engine’s environment variable secretKey: {“type”:“hmac”,“secret_key”:secretKey}. Same shape as the hmac variant of the Node SDK’s HttpAuthConfig. Signature

Parameters

string
required

InferSchema

InferSchema reflects a JSON Schema for T, exposed for callers that want to build a registration manually or inspect the schema the typed API would send. Signature

InvocationFromContext

InvocationFromContext returns the invocation a handler’s ctx belongs to, remote or local. ok is false outside any handler. Signature
context.Context
required

MarshalMessage

MarshalMessage encodes a variant struct as a wire frame, injecting the “type” tag. Pass one of the *Message structs (by pointer or value) from this file. Signature

Parameters

any
required

MetadataFromContext

MetadataFromContext returns the per-invocation metadata attached to a handler’s ctx. The bool is false (and the value nil) when the invocation carried no metadata, letting a handler distinguish “no metadata” from a present-but-empty value. Signature
context.Context
required

New

New creates a Client for the engine at url (e.g. DefaultEngineURL). An empty url means EngineURLFromEnv: III_URL when set, else DefaultEngineURL. It does not connect; call Client.Connect to start the connection lifecycle, or use RegisterWorker to create and connect in one step. Signature

Parameters

string
required
...Option

ObserveRejection

ObserveRejection builds the error an OnObserverAdded hook returns to reject an observer with code (any other error rejects it with OBSERVE_REJECTED). Signature

Parameters

string
required
string
required

OpenReader

OpenReader returns a reader for the read end described by ref, against the given engine WS base (typically Client.Address()). The socket connects on first read and authenticates with III_TOKEN, when set; channels from Client.CreateChannel also send the client’s WithHeaders. Prefer Client.OpenReader, which uses the client’s address and headers. Signature

Parameters

string
required
StreamChannelRef
required

OpenWriter

OpenWriter returns a writer for the write end described by ref, against the given engine WS base (typically Client.Address()). The socket connects on first send and authenticates with III_TOKEN, when set; channels from Client.CreateChannel also send the client’s WithHeaders. Prefer Client.OpenWriter, which uses the client’s address and headers. Signature

Parameters

string
required
StreamChannelRef
required

RegisterFunctionTyped

RegisterFunctionTyped registers a function whose request and response schemas are inferred from the Req and Resp type parameters and advertised to the engine. It is the schema-aware counterpart of Client.RegisterFunction; reach for it when you want the engine (and its dashboard / typed callers) to know the function’s contract. It returns the function’s handle, as Client.RegisterFunction does. Use Client.RegisterFunction directly for schemaless functions. See InferSchema to obtain a type’s schema on its own. Pass a single RegisterFunctionOptions value to attach a description, registration metadata or observe hooks; its RequestFormat and ResponseFormat, when set, are sent instead of the inferred schemas (that type is then not reflected). Signature
*Client
required
string
required
TypedHandler[Req, Resp]
required
...RegisterFunctionOptions

UnmarshalMessage

UnmarshalMessage decodes a wire frame by peeking at “type” and then decoding into the matching variant struct. It is the Go counterpart of serde’s tag dispatch. Signature

Parameters

[]byte
required

VoidAction

VoidAction returns the fire-and-forget action. A trigger with this action carries no invocation_id, so the engine sends no reply (see Client.Trigger). Signature

WithDescription

WithDescription sets a one-line, human/LLM-readable summary of what this worker does. Surfaces in engine::workers::list / engine::workers::info. Signature

Parameters

string
required

WithHeaders

WithHeaders sets HTTP headers sent on the WebSocket handshake of the main connection and of channels created with Client.CreateChannel. The III_TOKEN environment variable, when set and not blank, adds “Authorization: Bearer <token>” unless h already carries an Authorization header. Signature

Parameters

http.Header
required

WithInvocationTimeout

WithInvocationTimeout sets how long Client.Trigger waits for a result when TriggerRequest.Timeout is zero, in place of DefaultInvocationTimeout. It is the invocationTimeoutMs option of the Node SDK’s registerWorker. A d of zero or less keeps the default. Signature

Parameters

time.Duration
required

WithMetricsReporting

WithMetricsReporting turns the worker resource gauges on or off (Node enableMetricsReporting): the iii.worker.memory.*, iii.worker.cpu.*, iii.worker.event_loop.lag_ms and iii.worker.uptime_seconds metrics, tagged with worker.id and worker.name. The default is true. The gauges start when the engine acknowledges the worker and stop when the connection drops; they need telemetry and its metrics to be enabled (see OtelConfig). Signature

Parameters

bool
required

WithName

WithName sets the worker name reported to the engine. A non-empty III_WORKER_NAME takes precedence. The default is “hostname:pid”. Signature

Parameters

string
required

WithNamespace

WithNamespace sets the namespace this worker registers into. Takes precedence over the III_NAMESPACE environment variable. A namespace named and left blank is refused, not read as “no namespace”: the client is put in a terminal failed state, so Client.Connect returns the reason and Client.FatalError reports it. Absent and blank ask for opposite things: absent asks for the engine’s default, blank names a namespace and gives nothing to name it with. Read as absent, the worker registers in default, and since a worker’s calls and triggers follow its namespace, the whole project quietly serves from a place its declaration never named. To register in the engine’s default namespace, do not call this. Signature

Parameters

string
required

WithOtel

WithOtel configures the client’s OpenTelemetry pipeline (the otel option of Node registerWorker). Telemetry starts with the connection lifecycle (RegisterWorker or Client.Connect) and Client.Close flushes and stops it. Without this option the defaults documented on OtelConfig apply, and they enable telemetry. Signature
OtelConfig
required

WithReconnectConfig

WithReconnectConfig overrides the default reconnect schedule. Signature

Parameters

ReconnectConfig
required

WithTelemetry

WithTelemetry sets what the worker reports about its language, project and framework on every connection. Blank fields keep their defaults (see TelemetryOptions). Signature

Parameters

TelemetryOptions
required

filter.Compile

Compile validates and compiles a filter given as a Go value. A json.RawMessage or []byte is read as JSON text; any other value is read through encoding/json, so what is validated is exactly what travels on the wire. It returns an *Error with code INVALID_FILTER when the filter is not valid. Signature

Parameters

any
required

filter.MatchAll

MatchAll returns the filter that matches every document ({}). Signature

filter.Parse

Parse validates and compiles a filter given as JSON text. It returns an *Error with code INVALID_FILTER when the filter is not valid. Signature

Parameters

[]byte
required

filter.ParseNormalized

ParseNormalized compiles a filter in the normal form the engine pushes (functionregistered, observeradded). Every rule applies except the encoded size limit, which the engine checked on the filter as written (a normal form can be longer). Signature

Parameters

[]byte
required

Constants

iii

EngineFunctions are the engine’s built-in function paths a worker can invoke via Trigger. Mirrors EngineFunctions in the Node SDK. Naming note (kept verbatim from the Node SDK so the two read the same): ListTriggers / InfoTriggers cover trigger TYPES (templates); ListRegisteredTriggers / InfoRegisteredTriggers cover trigger INSTANCES (subscriber rows). Engine trigger types. Mirrors EngineTriggers in the Node SDK. Engine-hosted source functions (auto delivery): observe them with Client.Observe and filters, in place of the engine trigger types. Log function paths. Mirrors LogFunctions in the Node SDK. Invoke these with Trigger (fire-and-forget) to write to the engine log. Features this SDK declares in its engine::workers::register payload. The engine advertises the first two in WorkerRegistered. FeatureLargeMessagesV1 is declared by the SDK only: it receives JSON messages up to 64 MiB, so the engine sends it messages of that size whatever version it reports. Engine functions of the observer registry.

iii/filter

Structural limits of a filter (the conformance vectors define how they count).

Variables

iii

Sentinel errors for the two failure modes that carry no payload. Compare with errors.Is. These line up with the Rust IIIError::NotConnected / ::Timeout variants.

Types

iii

Package iii is a Go SDK for the iii worker protocol. Activation · Args · Caller · Capture · Channel · ChannelDirection · ChannelReader · ChannelWriter · ConnectionState · DecodedMessage · Deliver · Delivery · Dispatch · DroppedReports · ErrorBody · Filters · FunctionOptions · FunctionRef · FunctionRegisteredMessage · HTTPInvocationRef · Handler · Invocation · InvocationError · InvocationResultMessage · InvocationsObservedMessage · InvokeFunctionMessage · LegacyTrigger · LocalFunctionStats · LocalInvocationStatsMessage · MessageType · MiddlewareFunctionInput · ObserveDescriptor · ObserveDoc · ObserveHooks · ObserveMessage · ObserveMessageSource · ObserveMessageTarget · ObserveReason · ObserveRejectionError · ObserveResultMessage · Observed · ObservedItem · Observer · ObserverAckMessage · ObserverAddedMessage · ObserverHandle · ObserverInfo · ObserverOptions · ObserverRemovedMessage · ObserverState · ObserverStateChangedMessage · On · Op · Option · OtelConfig · PingMessage · PongMessage · ReattachMessage · ReconnectConfig · RegisterFunctionMessage · RegisterFunctionOptions · RegisterServiceMessage · RegisterTriggerInput · RegisterTriggerMessage · RegisterTriggerTypeMessage · RegistrationRejectedError · RegistrationRejectedMessage · Source · StreamChannelRef · TelemetryOptions · Trigger · TriggerAction · TriggerRegistrationResultMessage · TriggerRequest · TriggerTypeRef · TypedHandler · UnobserveMessage · UnregisterFunctionMessage · UnregisterTriggerMessage · UnregisterTriggerTypeMessage · WorkerRegisteredMessage

Activation

Activation marks the invocation of an observer’s target.

Args

Args are an observer’s arguments, for the observed function’s owner (owner-delivered functions only; validated against its args_format by the engine).

Caller

Caller is who started an invocation: the worker (WorkerID / WorkerName, stamped by the engine and never forgeable), and the function and invocation the call was made from. Parent is the caller of that handler, one level only. Every field may be empty: a top-level call has no function.

Capture

Capture names a part of an observed invocation shipped to an observer’s target. The default is input, output and caller.

Channel

Channel is a freshly created channel: a live writer/reader plus the refs for each end. Pass WriterRef or ReaderRef to another worker (in a trigger payload) so it opens the opposite end with Client.OpenReader / Client.OpenWriter. Created by Client.CreateChannel.

ChannelDirection

ChannelDirection is the end of a streaming channel a StreamChannelRef refers to. On the wire it is lowercase: “read” or “write”.

ChannelReader

ChannelReader is the read end of a channel: a WebSocket opened lazily on first use. Binary frames are stream data (NextBinary / ReadAll); text frames are messages delivered to OnMessage callbacks. The reader reads from a single goroutine internally, so register OnMessage callbacks before the first NextBinary/ReadAll call.

ChannelWriter

ChannelWriter is the write end of a channel: a WebSocket opened lazily on first use. SendMessage emits a text frame; Write emits 64 KiB-chunked binary frames. Close finishes the stream. A ChannelWriter is safe for serial use by one goroutine; it is not designed for concurrent writers (mirroring the reference SDKs).

ConnectionState

ConnectionState is the lifecycle state of a Client’s WebSocket. Mirrors IIIConnectionState in the Node SDK.

DecodedMessage

DecodedMessage is the result of UnmarshalMessage: the decoded “type” plus exactly one populated variant pointer (the rest are nil). Callers switch on Type, or check which pointer is non-nil.

Deliver

Deliver selects what an observer’s target receives: the whole Observed envelope (the default), or only the observed input or output.

Delivery

Delivery is how a function’s observers are delivered.

Dispatch

Dispatch selects how Client.Trigger reaches a function this worker hosts.

DroppedReports

DroppedReports counts report items the SDK dropped (BUFFER_FULL, TOO_LARGE).

ErrorBody

ErrorBody is the wire representation of a remote error: a code, a message and an optional stack trace. It is intentionally minimal; a Client.Trigger caller receives it as an InvocationError (read it with errors.As).

Filters

Filters is a declarative filter over input, output, error, caller and metadata, with explicit operators only (the language of the filter subpackage):

FunctionOptions

FunctionOptions is another name for RegisterFunctionOptions, the one the cross-SDK specification uses.

FunctionRef

FunctionRef is the handle of a registered function, returned by Client.RegisterFunction, Client.RegisterHTTPFunction, RegisterFunctionTyped and TriggerTypeRef.RegisterFunction. It mirrors the FunctionRef of the Node SDK.

FunctionRegisteredMessage

FunctionRegisteredMessage is the RegisterFunction success ack, with the full current observer set. Always accepted: it replaces the set the SDK holds.

HTTPInvocationRef

HTTPInvocationRef describes an externally-hosted function the engine calls directly over HTTP: the Node SDK’s HttpInvocationConfig. Register one with Client.RegisterHTTPFunction; it travels as the registration’s “invocation” field. Auth is raw JSON because the engine’s HttpAuthConfig is a tagged union: build it with HMACAuth, BearerAuth or APIKeyAuth.

Handler

Handler is a registered function’s implementation. data is the raw JSON the engine sent. The returned value is marshaled into the InvocationResult.result. Returning an error produces an InvocationResult.error; if the error is an *InvocationError its code and stacktrace are preserved, otherwise it is reported with code “invocation_failed” (matching the Rust and Node SDKs). Per-invocation metadata, when the call carries any, rides on ctx rather than the signature (so adding it is non-breaking): read it with MetadataFromContext.

Invocation

Invocation is the invocation a handler runs in, remote or local (InvocationFromContext).

InvocationError

InvocationError wraps a remote ErrorBody returned by the engine in InvocationResult.error, annotated with the function that was invoked. It is the Go counterpart of Node’s IIIInvocationError: one error type across all remote failure modes (RBAC FORBIDDEN, handler error, …), disambiguated by Code. Recover the details with errors.As:

InvocationResultMessage

InvocationResult is the worker’s reply to a non-fire-and-forget InvokeFunction. InvocationID is REQUIRED (a value, not a pointer): a result with no id cannot be routed back to its caller. Exactly one of Result/Error is set.

InvocationsObservedMessage

InvocationsObservedMessage carries matched local invocations of auto functions and obs.Emit events of owner functions, batched.

InvokeFunctionMessage

InvokeFunction is the engine->worker (and worker->engine, via Trigger) call. InvocationID is a POINTER and omitempty: when absent, the call is fire-and-forget and no InvocationResult is expected. Traceparent/Baggage carry W3C trace context across the hop. Action selects void/enqueue semantics. Metadata is OPTIONAL per-invocation metadata (arbitrary JSON) that travels as its own channel alongside Data, NOT folded into the payload. Like the engine’s skip_serializing_if optional fields it is omitted when nil; an inbound frame without a metadata key decodes to nil (“no metadata”), so older engines that never send it stay backward compatible. Distinct from RegisterFunction/RegisterTrigger’s registration-level Metadata: this one is scoped to a single call.

LegacyTrigger

LegacyTrigger is the old trigger an observer was created from by the engine’s legacy shim: the owner reads Config as the observer’s args.

LocalFunctionStats

LocalFunctionStats counts one function’s local invocations in a stats window.

LocalInvocationStatsMessage

LocalInvocationStatsMessage reports local invocations and SDK-side report drops, periodically and only when non-zero.

MessageType

MessageType is the value of the envelope “type” field: the lowercase name of the message variant, as the engine expects it.

MiddlewareFunctionInput

MiddlewareFunctionInput is the payload the engine sends to the RBAC middleware function (the worker-manager rbac.middleware_function_id) on every function invocation that arrives through the RBAC port. The middleware can inspect, modify or reject the call before it reaches the target function: forward it with Client.Trigger, or return an error to reject it. It mirrors MiddlewareFunctionInput in the Node and Rust SDKs field for field; the JSON names are the wire contract. Register the middleware with RegisterFunctionTyped to receive it decoded, or unmarshal the raw handler payload into it. When forwarding, note that an empty Namespace means the engine’s default namespace, whereas an empty TriggerRequest.Namespace means this worker’s own namespace: pass “default” explicitly when Namespace is empty and the worker is namespaced.

ObserveDescriptor

ObserveDescriptor is RegisterFunction.observe: the four fields of ObserveHooks that travel. The callbacks stay in the SDK.

ObserveDoc

ObserveDoc is the document an observer’s filters read (Observer.Matches). A nil field is absent; use json.RawMessage(null) for a JSON null.

ObserveHooks

ObserveHooks is the Observe option of RegisterFunctionOptions: how the function’s observers are delivered, and the callbacks that run when one is added or removed. Only Delivery, ArgsFormat, LegacyTriggerType and Allow travel to the engine. The callbacks of one function run one at a time, in revision order. A callback still running after the 30 s timeout no longer holds the queue (its observer is rejected with OWNER_TIMEOUT and its ctx cancelled), so a hung callback cannot stall the function forever: if it ignores ctx, it may overlap with the next callbacks.

ObserveMessage

ObserveMessage creates, or idempotently replays, an observer owned by this connection: Source is the left side of Client.Observe, Target the right side.

ObserveMessageSource

ObserveMessageSource is what an observer observes. Capture is omitted when nil and sent when empty (capture: [] is valid: ids, status and timings only).

ObserveMessageTarget

ObserveMessageTarget is the function an observer invokes.

ObserveReason

ObserveReason is why an observer is in its state: a machine-readable code and a message.

ObserveRejectionError

ObserveRejectionError is an observe error carrying its code: what ObserverHandle.Ready returns when the observer turns error or disposed, and what an ObserveHooks.OnObserverAdded hook returns (built with ObserveRejection) to reject an observer with a code of its own. Recover it with errors.As.

ObserveResultMessage

ObserveResultMessage is the engine’s reply to an observe (also on a replay).

Observed

Observed is what the target of an auto observer, or of obs.Emit, receives with DeliverEnvelope (the default). Fields not in the observer’s capture are absent. Decode a target’s payload into it:

ObservedItem

ObservedItem is one reported invocation or event. Input, Output, Error and Metadata keep JSON null apart from absent: “output”: null is a function that returned null, a nil Output was not captured.

Observer

Observer is an observer as the observed function’s owner sees it (in ObserveHooks.OnObserverAdded and Client.Observers): its args, filters, target, capture and on. Never its metadata, policy or the observing worker. Its fields are set when it is added; the SDK keeps its own copy of what it reads, so changing them changes nothing but the owner’s view. The pointer is stable while the observer exists, so owners keep it in their own index (expression -> observers, route table).

ObserverAckMessage

ObserverAckMessage is the owner’s answer to one added observer, sent after its OnObserverAdded hook returned. Error rejects it; an owner may re-send it with an error for an active observer (a late rejection).

ObserverAddedMessage

ObserverAddedMessage attaches one observer to a function this connection hosts.

ObserverHandle

ObserverHandle is what Client.Observe returns: the observing side of one observer. It is kept for replay, with the same id, on every connection until it is disposed. Safe for concurrent use.

ObserverInfo

ObserverInfo is an observer as the owner sees it: never its metadata, policy or the observing worker. Filters are in normal form.

ObserverOptions

ObserverOptions are the observer’s own settings: its id, policy and metadata. A zero field is unset.

ObserverRemovedMessage

ObserverRemovedMessage detaches one observer.

ObserverState

ObserverState is an observer’s lifecycle: pending (no owner yet, waiting for the owner’s ack, or no target yet) -> active or error; suspended while its worker or target is away; disposed at the end.

ObserverStateChangedMessage

ObserverStateChangedMessage is a lifecycle transition of an observer this connection owns.

On

On selects which invocations of an auto function reach an observer. The default is OnSuccess.

Op

Op is the operator object of one filter path: iii.Op{“$eq”: “insert”}.

Option

Option configures a Client. Pass options to New.

OtelConfig

OtelConfig configures the OpenTelemetry pipeline a Client runs: spans, metrics and logs exported to the engine over a dedicated WebSocket at <engine address>/otel, the “execute <function id>” span around every handler, and the worker resource gauges. It mirrors the Node SDK’s OtelConfig (the otel option of registerWorker) field for field. The engine URL and the handshake headers are not part of it: the client uses its own address and its WithHeaders headers (plus the III_TOKEN bearer), as Node does for engineWsUrl and engineWsHeaders. Telemetry is enabled by default, as in the Node SDK: a client started without WithOtel exports unless OTEL_ENABLED is “false”, “0”, “no” or “off”. A zero field means “not set”: the environment variable named on the field, then the default, fills it in. OpenTelemetry globals: when telemetry starts, the client installs its tracer provider, its meter provider and the W3C Trace Context + Baggage propagator as the OpenTelemetry globals (otel.Tracer, otel.Meter, otel.GetTextMapPropagator), each only while that global is still the otel default. A provider or propagator the application installed earlier, or another client installed first, is never replaced: first registration wins, as in the Node SDK. Client.Close puts the default back into every global that still holds this client’s. The client’s invocation spans and worker gauges, and the observability helpers (which use the client started last), always use the client’s own providers, so they reach the engine either way. Spans the application creates with its own provider are parented to the invocation span through ctx and exported wherever that provider exports. Trigger and inbound invocations always propagate W3C Trace Context and Baggage, whatever the global propagator.

PingMessage

PingMessage is the payloadless keepalive the engine sends; it serializes to {“type”:“ping”}. The client replies with a PongMessage.

PongMessage

PongMessage is the payloadless reply to a PingMessage; it serializes to {“type”:“pong”}.

ReattachMessage

Reattach is sent worker->engine as the first message of a reconnect, before the registration replay: PreviousWorkerID is the id the engine assigned via WorkerRegistered on the previous connection. The engine retires that connection so the replay lands on a clean slate instead of racing its cleanup.

ReconnectConfig

ReconnectConfig controls the exponential-backoff-with-jitter reconnect loop. The defaults below match the Node SDK’s DEFAULT_BRIDGE_RECONNECTION_CONFIG exactly, so a Go worker reconnects on the same schedule as a Node one.

RegisterFunctionMessage

RegisterFunction announces a function this worker can handle. RequestFormat and ResponseFormat are optional JSON Schemas; Invocation is set only for externally HTTP-hosted functions (Client.RegisterHTTPFunction). Optional fields are omitted when unset, as the engine writes them (skip_serializing_if); the engine reads an absent format and a JSON null alike. Observe is the function’s observe descriptor: how its observers are delivered. Absent means delivery auto, observable, no args.

RegisterFunctionOptions

RegisterFunctionOptions configures a function registration. The zero value preserves the default registration shape. FunctionOptions is the same type.

RegisterServiceMessage

RegisterService groups functions under a service for the dashboard.

RegisterTriggerInput

RegisterTriggerInput is the input of Client.RegisterTrigger: fire FunctionID when a trigger of Type matches Config. It mirrors RegisterTriggerInput in the Node SDK.

RegisterTriggerMessage

RegisterTrigger registers a trigger *instance* that fires FunctionID when its trigger type matches. The trigger type travels in the wire field “trigger_type”, the name the engine reads (the Node SDK’s “type” option is renamed to it on the wire).

RegisterTriggerTypeMessage

RegisterTriggerType registers a trigger *template* (e.g. “http”, “cron”). The two *_format fields are optional JSON Schemas describing the trigger config and the resulting function-call payload.

RegistrationRejectedError

RegistrationRejectedError is the terminal error the engine returns when a worker’s registration is refused for good, typically a WORKER_NAMESPACE_CONFLICT, where another live worker already owns this name in the namespace. It is delivered to every pending invocation and reported by Client.FatalError; the worker stops and does not reconnect. Mirrors the Node/Python/Rust SDKs. Recover the details with errors.As:

RegistrationRejectedMessage

RegistrationRejectedMessage is the engine’s refusal of a registration. A FUNCTION_NAMESPACE_CONFLICT costs one function and leaves the connection open; a WORKER_NAMESPACE_CONFLICT is terminal: another live worker owns this name in the namespace.

Source

Source is the left side of Client.Observe: what is observed.

StreamChannelRef

StreamChannelRef is a capability handle to one end of a streaming data channel. The engine’s engine::channels::create returns a writer ref and a reader ref that share a channel_id and access_key; a ref travels as plain JSON inside a trigger payload or result, and the holder opens its own WebSocket to the channel with it (Client.OpenReader, Client.OpenWriter).

TelemetryOptions

TelemetryOptions is what the worker reports about its language, project and framework in the telemetry object of engine::workers::register, shown by engine::workers::list and engine::workers::info. A blank field takes its default. Mirrors TelemetryOptions in the Node and Rust SDKs.

Trigger

Trigger is the handle of a registered trigger, returned by Client.RegisterTrigger and TriggerTypeRef.RegisterTrigger. It mirrors the Trigger of the Node SDK.

TriggerAction

TriggerAction mirrors the engine’s TriggerAction enum, a “type”-tagged lowercase union: {“type”:“void”} or {“type”:“enqueue”,“queue”:”…”}. It rides on InvokeFunction.Action and selects the delivery semantics of a Trigger call.

TriggerRegistrationResultMessage

TriggerRegistrationResult is the engine’s ack for a RegisterTrigger; Error is set only on failure.

TriggerRequest

TriggerRequest is the input to Client.Trigger. The Action field selects the delivery semantics: nil/await (default) waits for the result; VoidAction is fire-and-forget; EnqueueAction routes through a named queue and awaits its receipt.

TriggerTypeRef

Deprecated. Trigger types are replaced by functions with an observe descriptor, and these helpers by Client.Observe. Migration guide: https://iii.dev/docs/upgrading/from-0-24-x. TriggerTypeRef is the handle of a registered trigger type, returned by Client.RegisterTriggerType. It registers triggers and functions bound to the type without repeating its id, and removes the type. It mirrors the TriggerTypeRef of the Node SDK.

TypedHandler

TypedHandler is a function handler with a typed request and response. The SDK unmarshals the invocation payload into Req before calling it and marshals the returned Resp into the result, so handlers work with concrete types instead of json.RawMessage. Per-invocation metadata, when the call carries any, rides on ctx rather than the signature (so adding it is non-breaking): read it with MetadataFromContext.

UnobserveMessage

UnobserveMessage removes an observer this connection owns.

UnregisterFunctionMessage

UnregisterFunction removes a previously registered function.

UnregisterTriggerMessage

UnregisterTrigger removes a trigger instance. TriggerType is optional on the wire, so it is a pointer.

UnregisterTriggerTypeMessage

UnregisterTriggerTypeMessage retires a trigger type this connection provides. The engine removes it only when the sending connection is its provider. Namespace absent means the sending connection’s namespace.

WorkerRegisteredMessage

WorkerRegistered is sent engine->worker on connect to announce the worker’s id. The worker treats it as informational.

iii/filter

Package filter is the observer filter language (iii-filter v1): validation and evaluation with the same semantics as the engine’s evaluator and the other SDKs, pinned down by the conformance vectors all of them share. Doc · Error · ErrorCode · Filter · Map · Root · Roots

Doc

Doc is the document a filter reads: the value of each root, and whether it is present. A missing root is absent; a present nil is JSON null.

Error

Error is a filter the language rejects. Recover it with errors.As.

ErrorCode

ErrorCode is the protocol error code of a rejected filter.

Filter

Filter is a validated filter, compiled once into a closure tree. It is immutable and safe for concurrent use.

Map

Map is a Doc backed by a map keyed by root name: a missing key is an absent root, a nil value is JSON null. Keys other than the five roots are ignored.

Root

Root is a path’s first segment: the part of the document it reads.

Roots

Roots tells which document roots a filter’s clauses read.