Next.js — examples

Beyond the minimal binding snippet — the patterns examples/nextjs is built on: composing a data layer, slicing shared fields, and driving the UI off task state.

A data-layer hook

The same incidents pattern as the React demo — the hook is a client-boundary module; seed.runOnce() ignores repeats while pending/settled and the page query re-runs latest-wins on spec change.

src/useIncidents.tsfrontend
'use client';

export function useIncidents(query: QueryArgs) {
  const seed = useTask(initIncidents);             // one-shot bootstrap
  const page = useTask(incidents.queryIncidents);  // latest-wins query
  const seedProgress = useSharedValue(incidentsMemory, 'signals.seedProgress');
  const metrics = useSharedValue(incidentsMemory, 'state.metrics');

  useEffect(() => seed.runOnce(), []);
  useEffect(() => {
    if (seed.settled) page.run(query);
  }, [seed.settled, query]);

  return {
    ready: seed.settled,
    seedProgress: seedProgress ?? 0,
    metrics: metrics ?? null,
    page: page.data,
    isFetching: page.pending,
  };
}

Live fields in any client component

Any number of client components can bind the same shared field — each subscribes independently and tracks the worker's writes.

components/SeedProgress.tsxfrontend
'use client';

import { useSharedValue } from '@atolljs/nextjs';
import { incidentsMemory } from '@atolljs/incidents';

export function SeedProgress() {
  const progress = useSharedValue(incidentsMemory, 'signals.seedProgress');
  return <progress value={progress ?? 0} max={1} />;
}