Clients

Clients

Clients are used to get and communicate with actors from your application. Clients can be created from either your frontend or backend.

Creating a Client

For frontend applications or external services:

import { createClient } from "rivetkit/client";
import type { registry } from "./registry";  // Must use `type`

const client = createClient<typeof registry>();

Getting an Actor

getOrCreate

Returns a handle to an existing actor or creates one if it doesn't exist:

const counter = client.counter.getOrCreate("my-counter");
const count = await counter.increment(5);

Pass initialization data when creating:

const game = client.game.getOrCreate("game-123", {
  createWithInput: { gameMode: "tournament", maxPlayers: 8 }
});

get

Returns a handle to an existing actor or null if it doesn't exist:

const handle = client.myActor.get("actor-id");

if (handle) {
  await handle.someAction();
}

create

Creates a new actor, failing if one already exists with that key:

const newGame = await client.game.create("game-456", {
  input: { gameMode: "classic" }
});

getForId

Connect to an actor using its internal ID:

const actor = client.myActor.getForId("lrysjam017rhxofttna2x5nzjml610");

Prefer using keys over internal IDs for simplicity.

Calling Actions

const counter = client.counter.getOrCreate("my-counter");

const count = await counter.increment(5);
const value = await counter.getCount();
await counter.reset();

In JavaScript, actions called without connect() are stateless. Each call is independent without a persistent connection. In React, useActor automatically manages a persistent connection.

Connecting to an Actor

For real-time use cases, establish a persistent connection to the actor:

const counter = client.counter.getOrCreate("live-counter");
const conn = counter.connect();

// Listen for events
conn.on("countChanged", (newCount: number) => {
  console.log("Count updated:", newCount);
});

// Call actions through the connection
await conn.increment(1);

Subscribing to Events

Listen for events from connected actors:

const conn = client.chatRoom.getOrCreate("general").connect();

// Listen for events
conn.on("messageReceived", (message) => {
  console.log(`${message.from}: ${message.text}`);
});

// Listen once
conn.once("gameStarted", () => {
  console.log("Game has started!");
});

Full-Stack Type Safety

Import types from your registry for end-to-end type safety:

import { createClient } from "rivetkit/client";
import type { registry } from "./registry";

const client = createClient<typeof registry>();

// IDE autocomplete shows available actors and actions
const counter = client.counter.getOrCreate("my-counter");
const count = await counter.increment(5);

Use import type to avoid accidentally bundling backend code in your frontend.

Advanced

Disposing Clients & Connections

Dispose clients to close all connections:

await client.dispose();
TypeScript

Dispose individual connections when finished:

const conn = actor.connect();

try {
  conn.on("event", handler);
  await conn.action();
} finally {
  await conn.dispose();
}
TypeScript

When using useActor in React, connections are automatically disposed when the component unmounts. No manual cleanup is required.

Connection Parameters

Pass custom data to the actor when connecting:

const chat = client.chatRoom.getOrCreate("general", {
  params: {
    userId: "user-123",
    displayName: "Alice"
  }
});

Authentication

Pass authentication tokens when connecting:

const chat = client.chatRoom.getOrCreate("general", {
  params: {
    authToken: "jwt-token-here"
  }
});

See authentication for more details.

Error Handling

import { ActorError } from "rivetkit/client";

const conn = actor.connect();
conn.onError((error: ActorError) => {
  if (error.code === "forbidden") {
    window.location.href = "/login";
  }
});

See errors for more details.

Actor Resolution

get and getOrCreate return immediately without making a network request. The actor is resolved lazily when you call an action or connect().

To explicitly resolve an actor and get its ID, use resolve():

const handle = client.counter.getOrCreate("my-counter");
const actorId = await handle.resolve();
console.log(actorId); // "lrysjam017rhxofttna2x5nzjml610"
TypeScript

API Reference

Suggest changes to this page