hello-rivet-next: The End of the REST API for Real-Time Apps

How a bleeding-edge reference architecture uses the Actor model to replace event-driven boilerplate with fully typed, synchronized shared state.

6 min read • View on GitHub • More from manaflow-ai

A vast, pristine clockwork mechanism where multiple distinct pendulums swing in perfect unison, pulling fine taut threads. This represents synchronized distributed state across multiple clients.
The Actor model enforces perfect synchronization across distributed clients without manual event routing.
Key Takeaways

The GUI Tax on Real-Time State

Next.js handles standard CRUD applications beautifully. You fetch data, render UI, and mutate state via server actions. But the moment an application requires real-time multiplayer features, the architectural complexity explodes.

Building live cursors, shared counters, or collaborative documents usually requires a massive amount of boilerplate. Developers are forced to manually orchestrate WebSockets, build custom event routers, and maintain complex Redux or Saga architectures just to keep clients in sync. This is the real-time tax.

An old-fashioned telephone switchboard overflowing with a chaotic, tangled mess of cables. The operator's hands are a blur trying to plug and unplug cables into unmarked sockets. Represents the traditional WebSocket/Redux boilerplate.
Managing custom WebSockets and event listeners quickly degrades into a tangled switchboard of state mutations.

Hiring Actors for the Frontend

The hello-rivet-next repository demonstrates a paradigm shift. It introduces the Rivetkit Actor model to the Next.js frontend. Instead of writing custom routing logic for every state mutation, developers define an Actor.

An Actor is a stateful entity that holds its own data and broadcasts changes automatically. When a client calls a method on an Actor, the framework handles the complex fan-out broadcasting to all connected clients. The mental model shifts from fetching data to connecting to a living instance.

The Actor model handles the complex pub/sub fan-out automatically, allowing developers to call remote functions as if they were local.

The Source of Truth Contract

The technical meat of the project lives in registry.ts. This file defines the state object and its available actions. The true power unlocks when this registry is passed to the Next.js client.

By passing typeof registry to the frontend, Rivet creates an unbreakable, type-safe contract. Backend changes instantly flag frontend compilation errors, providing 100 percent end-to-end type safety for real-time events without requiring external generators like OpenAPI.

import { actor } from 'rivetkit';

export const counterActor = actor({
  state: { count: 0 },
  actions: {
    increment: (c, amount: number) => {
      c.state.count += amount;
      c.broadcast('newCount', c.state.count);
    }
  }
});

Multiplayer by Default

On the client side, consuming this state is remarkably simple. The useActor hook allows developers to connect to an isolated instance using a unique key.

By simply changing the key array (e.g., ["room-123"]), developers spin up isolated, real-time rooms with a single line of code. The frontend interacts with remote state exactly as it would local React state.

FeatureTraditional REST + WebSocketRivet Actor Model
State LocationClient Cache + DatabaseIn-Memory Actor
CommunicationManual Fetch/Push & Socket ListenersAutomated Pub/Sub Sync
Type SafetyRequires external generators (OpenAPI)Native TypeScript inference
RoutingIndividual endpoint per actionSingle wildcard API bridge