Function-like calls
Call a worker function and await the result without maintaining worker files by hand.
React hooks for Web Workers
useWebWorker gives React apps a small function-style API for running expensive work in a Web Worker, with TypeScript inference, status tracking, timeout handling, and automatic cleanup.
pnpm add @atom-universe/use-web-workerimport { useWebWorkerFn } from '@atom-universe/use-web-worker';
function App() {
const [workerFn, status] = useWebWorkerFn(
(items: number[]) => items.reduce((total, item) => total + item, 0)
);
async function calculate() {
const result = await workerFn([1, 2, 3]);
console.log(result);
}
return <button onClick={calculate}>Run in worker: {status}</button>;
}Why workers
Call a worker function and await the result without maintaining worker files by hand.
Use the injected worker context to stream progress updates back to React state.
The hook terminates generated workers on completion, timeout, error, or unmount.
Benchmark
The reproducible script runs a Mandelbrot-style workload on the main thread and in a worker thread. Total runtime can be similar, but the worker path keeps frame scheduling available for the page.
Interactive comparison
The left panel runs a heavier Mandelbrot-style stress test on the main thread. The right panel uses a Web Worker, so the pulse indicator should keep moving while the canvas is generated.
Blocks the UI while computing.
Keeps the page responsive.
Reproducible script result
Lower timer gaps mean the main thread has more room to paint and respond to input.
11 missed 60Hz frames in the benchmark run.
0 missed 60Hz frames in the benchmark run.
Generated by pnpm benchmark on Node v22.22.0. Checksum matched: yes.
API quick reference
const [run, status, terminate] = useWebWorkerFn(fn, {
dependencies,
localDependencies,
timeout,
onError,
onMessage,
});PENDING4Idle or reset state
RUNNING3Worker is executing
SUCCESS0Last run completed
ERROR1Worker reported an error
TIMEOUT2Timeout guard fired
localDependencies accepts functions that are stringified into the generated worker. onMessage receives custom worker messages.
Examples
export function computeMandelbrot(
width: number,
height: number,
maxIterations: number,
workerContext: Worker
) {
workerContext.postMessage(['PROGRESS', { percent: 25 }]);
return new Array(width * height).fill(maxIterations);
}Known TODO
The documentation now reflects the current API. A later core pass should address blob URL cache keys, synchronous concurrent calls, cancellation semantics, and behavior-level hook tests.