clockworklabs/SpacetimeDB · error · Error

Could not find SpacetimeDB client! Did you forget to add a `

Error message

Could not find SpacetimeDB client! Did you forget to add a `SpacetimeDBProvider`? `useTable` must be used in the React component tree under a `SpacetimeDBProvider` component.

What it means

useTable calls useSpacetimeDB() inside a try/catch; if the React context is missing (no SpacetimeDBProvider above the component) it swallows the original error and rethrows this useTable-specific message. Root cause is identical to the useSpacetimeDB provider error - the client context is undefined.

Source

Thrown at crates/bindings-typescript/src/react/useTable.ts:81

 *   { onInsert: (row) => console.log('New user:', row) }
 * );
 * ```
 */
export function useTable<TableDef extends UntypedTableDef>(
  query: Query<TableDef>,
  callbacks?: UseTableCallbacks<Prettify<RowType<TableDef>>>
): [readonly Prettify<RowType<TableDef>>[], boolean] {
  type UseTableRowType = RowType<TableDef>;
  const enabled = callbacks?.enabled ?? true;
  const accessorName = getQueryAccessorName(query);
  const whereExpr = getQueryWhereClause(query);

  const [subscribeApplied, setSubscribeApplied] = useState(false);
  let connectionState: ConnectionState | undefined;
  try {
    connectionState = useSpacetimeDB();
  } catch {
    throw new Error(
      'Could not find SpacetimeDB client! Did you forget to add a ' +
        '`SpacetimeDBProvider`? `useTable` must be used in the React component tree ' +
        'under a `SpacetimeDBProvider` component.'
    );
  }

  const querySql = toSql(query);

  const latestTransactionEventId = useRef<string | null>(null);
  const lastSnapshotRef = useRef<
    [readonly Prettify<UseTableRowType>[], boolean] | null
  >(null);

  const computeSnapshot = useCallback((): [
    readonly Prettify<UseTableRowType>[],
    boolean,
  ] => {
    if (!enabled) {

View on GitHub (pinned to 524b4487d9)

Solutions

  1. Move <SpacetimeDBProvider> up so it is an ancestor of every component using useTable
  2. Verify the provider is not conditionally rendered or keyed away on the failing route
  3. In tests/stories, wrap with <SpacetimeDBProvider> or mock the SpacetimeDBContext module

Example fix

// before
export const App = () => (
  <>
    <SpacetimeDBProvider>{/* ... */}</SpacetimeDBProvider>
    <UserList /> {/* uses useTable, outside provider -> throws */}
  </>
);

// after
export const App = () => (
  <SpacetimeDBProvider>
    <UserList />
  </SpacetimeDBProvider>
);
Defensive patterns

Strategy: validation

Validate before calling

// Before adding useTable to a component, confirm the provider covers it:
<App>
  <SpacetimeDBProvider>
    <Routes /> {/* every useTable consumer lives here */}
  </SpacetimeDBProvider>
</App>

Try / catch

// Error boundary fallback for pages that may render outside the provider:
if (missingProvider) return <div>Connecting to SpacetimeDB...</div>;

Prevention

When it happens

Trigger: Calling useTable(table, query, callbacks) in a component that is rendered outside the <SpacetimeDBProvider> subtree.

Common situations: Adding useTable to a new screen while the provider only covers part of the tree; the provider mounted below (not above) the component; storybook/unit-test renders without the provider.

Related errors


AI-assisted analysis of clockworklabs/SpacetimeDB@524b4487d9 (2026-08-16). Data as JSON: /api/errors/03841878d0e42763. Report an issue: GitHub.