Skip to main content

Install

Define actors in src/actor.ts. Use standard TypeScript decorators; leave experimentalDecorators disabled. Keep the configuration from terse init.

Actor definitions

Import actor classes, decorators, and socket types from terse-sdk/actor. Extend Actor directly. Give fields defaults. Keep constructors free of external work. Make application methods async. Use concrete JSON-compatible argument and return types. Every instance field needs @Persisted or @Ephemeral. Private persisted fields stay outside emitted state. Use TypeScript private; JavaScript #private fields cannot use @Persisted.

Backend calls

Generate the client from your application project:
get() returns a reference. The first call activates the actor as needed. Use the same ID to reach the same state. Use the generated client for Terse connection settings. Set TERSE_ACTOR_URL and TERSE_API_KEY on the calling backend for hosted actors.

Browser access

Authenticate the user. Check access to the actor ID. Derive metadata on your backend. Issue a grant:
Return the grant with Cache-Control: no-store. The browser opens new WebSocket(grant.websocketUrl). It sends JSON.stringify({ by: 1 }). ActorProxy.handle({ actorName, actorId, metadata }) provides the same grant flow through the generated ActorProxy export.

Socket handlers

Broadcast options accept except, tags, and tagMatch: "all" | "any". Socket metadata and tags last for that connection.

Streaming and state

Broadcast inside the model’s streaming loop. Accumulate output locally. Assign the completed result to a persisted field before returning. Emitted fields use two wire messages:
Replace local state on state. Merge changes on state_update. Delete fields in removed. Keep application message types distinct from those two names. Broadcasts have no replay. Obtain a fresh grant on reconnect. Restore the saved snapshot. See the browser example.

Failures and concurrency

Ordinary calls serialize. Failed calls roll back persisted fields. Broadcasts and external writes can already have happened. ActorInvocationError with code outcome_unknown means the call may have executed. Reconcile saved state and external effects before retrying. @Reentrant permits overlap. It disables failure rollback across the actor class. See Concepts.