spacetimedb-best-practices

spacetimedb-best-practices

SpacetimeDB development best practices for TypeScript server modules and client SDK. This skill should be used when writing, reviewing, or refactoring SpacetimeDB code to ensure optimal patterns for real-time, multiplayer applications. Triggers on tasks involving SpacetimeDB modules, tables, reducers, subscriptions, or React integration.

0Star
0Fork
更新于 1/18/2026
SKILL.md
readonly只读
name
spacetimedb-best-practices
description

SpacetimeDB development best practices for TypeScript server modules and client SDK. This skill should be used when writing, reviewing, or refactoring SpacetimeDB code to ensure optimal patterns for real-time, multiplayer applications. Triggers on tasks involving SpacetimeDB modules, tables, reducers, subscriptions, or React integration.

version
"2.0.0"

SpacetimeDB Best Practices

Comprehensive development guide for SpacetimeDB applications, covering both TypeScript server modules and client SDK integration with React. Contains rules across 8 categories, prioritized by impact to guide automated refactoring and code generation.

Package: spacetimedb (v1.4.0+)

When to Apply

Reference these guidelines when:

  • Writing SpacetimeDB server modules in TypeScript
  • Designing table schemas and indexes
  • Implementing reducers for state mutations
  • Setting up client subscriptions and queries
  • Integrating SpacetimeDB with React applications
  • Optimizing real-time sync performance

Rule Categories by Priority

Priority Category Impact Prefix
1 Module Design CRITICAL module-
2 Table Schema & Indexing CRITICAL table-
3 Reducer Patterns HIGH reducer-
4 Subscription Optimization HIGH subscription-
5 Client State Management MEDIUM-HIGH client-
6 React Integration MEDIUM react-
7 TypeScript Patterns MEDIUM ts-
8 Real-time Sync LOW-MEDIUM sync-

Quick Reference

Server Module API (TypeScript)

import { spacetimedb, table, t, ReducerContext } from 'spacetimedb';

// Define tables with the table builder
const Player = table(
  { name: 'player', public: true },
  {
    identity: t.identity().primaryKey(),
    name: t.string(),
    score: t.u64().index(),
    isOnline: t.bool().index(),
  }
);

// Define reducers
spacetimedb.reducer('create_player', { name: t.string() }, (ctx: ReducerContext, { name }) => {
  ctx.db.player.insert({
    identity: ctx.sender,
    name,
    score: 0n,
    isOnline: true,
  });
});

// Lifecycle hooks
spacetimedb.init((ctx: ReducerContext) => { /* module init */ });
spacetimedb.clientConnected((ctx: ReducerContext) => { /* client connected */ });
spacetimedb.clientDisconnected((ctx: ReducerContext) => { /* client disconnected */ });

Client SDK API (TypeScript)

import { DbConnection } from './generated';

// Build connection
const conn = DbConnection.builder()
  .withUri('ws://localhost:3000')
  .withModuleName('my-module')
  .onConnect((ctx, identity, token) => {
    // Setup subscriptions
    conn.subscription(['SELECT * FROM player WHERE isOnline = true']);
  })
  .onDisconnect((ctx, error) => { /* handle disconnect */ })
  .build();

// Call reducers
await conn.reducers.createPlayer('Alice');

// Access tables
const player = conn.db.player.identity.find(identity);

React Integration

import { useTable, where, eq } from 'spacetimedb/react';
import { DbConnection, Player } from './generated';

function OnlinePlayers() {
  const { rows: players } = useTable<DbConnection, Player>(
    'player',
    where(eq('isOnline', true))
  );

  return players.map(p => <div key={p.identity.toHexString()}>{p.name}</div>);
}

Rule Categories

1. Module Design (CRITICAL)

  • module-single-responsibility - One module per domain concept
  • module-lifecycle - Use lifecycle hooks appropriately (init, clientConnected, clientDisconnected)
  • module-error-handling - Handle errors gracefully in module code
  • module-type-exports - Export types for client consumption

2. Table Schema & Indexing (CRITICAL)

  • table-primary-keys - Choose appropriate primary key strategies
  • table-indexing - Add .index() for frequently queried columns
  • table-relationships - Model relationships between tables correctly
  • table-column-types - Use appropriate SpacetimeDB types

3. Reducer Patterns (HIGH)

  • reducer-atomicity - Keep reducers atomic and focused
  • reducer-validation - Validate inputs at reducer entry
  • reducer-authorization - Check caller identity for sensitive operations
  • reducer-batch-operations - Batch related mutations in single reducer

4. Subscription Optimization (HIGH)

  • subscription-selective - Subscribe only to needed data
  • subscription-filters - Use subscription filters to reduce data transfer
  • subscription-cleanup - Clean up subscriptions when no longer needed
  • subscription-batching - Batch subscription setup on client connect

5. Client State Management (MEDIUM-HIGH)

  • client-connection-lifecycle - Handle connection/reconnection properly
  • client-optimistic-updates - Use optimistic updates for responsive UI
  • client-error-recovery - Handle reducer errors gracefully
  • client-identity - Manage identity tokens securely

6. React Integration (MEDIUM)

  • react-use-subscription - Use subscription hooks correctly
  • react-table-hooks - Use useTable<DbConnection, Type>() for reactive data
  • react-reducer-hooks - Call conn.reducers.* with proper error handling
  • react-connection-status - Display connection status to users

7. TypeScript Patterns (MEDIUM)

  • ts-generated-types - Use generated types from SpacetimeDB CLI
  • ts-strict-mode - Enable strict TypeScript for better type safety
  • ts-discriminated-unions - Use discriminated unions for state
  • ts-type-guards - Implement type guards for runtime validation

8. Real-time Sync (LOW-MEDIUM)

  • sync-conflict-resolution - Handle concurrent modifications
  • sync-offline-support - Design for offline-first when needed
  • sync-debounce-updates - Debounce rapid UI updates
  • sync-presence - Implement user presence efficiently

How to Use

Read individual rule files for detailed explanations and code examples:

rules/module-single-responsibility.md
rules/table-primary-keys.md
rules/_sections.md

Each rule file contains:

  • Brief explanation of why it matters
  • Incorrect code example with explanation
  • Correct code example with explanation
  • Additional context and references

Full Compiled Document

For the complete guide with all rules expanded: AGENTS.md

You Might Also Like

Related Skills

coding-agent

coding-agent

179Kdev-codegen

Run Codex CLI, Claude Code, OpenCode, or Pi Coding Agent via background process for programmatic control.

openclaw avataropenclaw
获取
add-uint-support

add-uint-support

97Kdev-codegen

Add unsigned integer (uint) type support to PyTorch operators by updating AT_DISPATCH macros. Use when adding support for uint16, uint32, uint64 types to operators, kernels, or when user mentions enabling unsigned types, barebones unsigned types, or uint support.

pytorch avatarpytorch
获取
at-dispatch-v2

at-dispatch-v2

97Kdev-codegen

Convert PyTorch AT_DISPATCH macros to AT_DISPATCH_V2 format in ATen C++ code. Use when porting AT_DISPATCH_ALL_TYPES_AND*, AT_DISPATCH_FLOATING_TYPES*, or other dispatch macros to the new v2 API. For ATen kernel files, CUDA kernels, and native operator implementations.

pytorch avatarpytorch
获取
skill-writer

skill-writer

97Kdev-codegen

Guide users through creating Agent Skills for Claude Code. Use when the user wants to create, write, author, or design a new Skill, or needs help with SKILL.md files, frontmatter, or skill structure.

pytorch avatarpytorch
获取

Implements JavaScript classes in C++ using JavaScriptCore. Use when creating new JS classes with C++ bindings, prototypes, or constructors.

oven-sh avataroven-sh
获取

Creates JavaScript classes using Bun's Zig bindings generator (.classes.ts). Use when implementing new JS APIs in Zig with JSC integration.

oven-sh avataroven-sh
获取