Offload functions to worker threads with shared memory primitives for Node.js.
8
fork

Configure Feed

Select the types of activity you want to include in your feed.

chore: prettier lint fixes across project

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

+27 -12
+1
README.md
··· 105 105 ``` 106 106 107 107 Built-in balancers: 108 + 108 109 - `roundRobin()` — cycles through workers in order (default) 109 110 - `leastBusy()` — picks the worker with the lowest active task count 110 111
+4 -1
src/dedicated-runner.ts
··· 48 48 const worker = getWorker(id); 49 49 ref(worker); 50 50 const { iterable, done } = dispatchStream<T>(worker, id, args); 51 - done.then(() => unref(worker), () => unref(worker)); 51 + done.then( 52 + () => unref(worker), 53 + () => unref(worker), 54 + ); 52 55 return iterable; 53 56 }
+3 -1
test/fixtures/load-balancing.ts
··· 10 10 11 11 export const busy = mo(import.meta, (ms: number): string => { 12 12 const start = Date.now(); 13 - while (Date.now() - start < ms) { /* busy wait */ } 13 + while (Date.now() - start < ms) { 14 + /* busy wait */ 15 + } 14 16 return 'done'; 15 17 });
+16 -5
test/load-balancing.test.ts
··· 80 80 it('balancer dispose is called on sync dispose', () => { 81 81 let disposed = false; 82 82 const custom: Balancer = { 83 - select(workers) { return workers[0]; }, 84 - [Symbol.dispose]() { disposed = true; }, 83 + select(workers) { 84 + return workers[0]; 85 + }, 86 + [Symbol.dispose]() { 87 + disposed = true; 88 + }, 85 89 }; 86 90 const run = workers(1, { balance: custom }); 87 91 run[Symbol.dispose](); ··· 91 95 it('balancer asyncDispose is called on async dispose', async () => { 92 96 let disposed = false; 93 97 const custom: Balancer = { 94 - select(workers) { return workers[0]; }, 95 - async [Symbol.asyncDispose]() { disposed = true; }, 98 + select(workers) { 99 + return workers[0]; 100 + }, 101 + async [Symbol.asyncDispose]() { 102 + disposed = true; 103 + }, 96 104 }; 97 105 const run = workers(1, { balance: custom }); 98 106 await run[Symbol.asyncDispose](); ··· 102 110 it('pinned tasks bypass balancer', async () => { 103 111 let called = false; 104 112 const custom: Balancer = { 105 - select(workers) { called = true; return workers[0]; }, 113 + select(workers) { 114 + called = true; 115 + return workers[0]; 116 + }, 106 117 }; 107 118 const run = workers(2, { balance: custom }); 108 119 try {
+3 -5
test/pool-ref.test.ts
··· 10 10 11 11 describe('pool worker ref behavior', () => { 12 12 it('pool keeps event loop alive for top-level await', async () => { 13 - const { stdout } = await exec( 14 - process.execPath, 15 - ['--no-warnings', join(fixturesDir, 'pool-ref-main.ts')], 16 - { timeout: 5000 }, 17 - ); 13 + const { stdout } = await exec(process.execPath, ['--no-warnings', join(fixturesDir, 'pool-ref-main.ts')], { 14 + timeout: 5000, 15 + }); 18 16 assert.ok(stdout.includes('DONE')); 19 17 }); 20 18 });