Latest Threat Research:SANDWORM_MODE: Shai-Hulud-Style npm Worm Hijacks CI Workflows and Poisons AI Toolchains.Details
Socket
Book a DemoInstallSign in
Socket

@rushstack/worker-pool

Package Overview
Dependencies
Maintainers
3
Versions
220
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@rushstack/worker-pool - npm Package Compare versions

Comparing version
0.4.81
to
0.5.0
+12
-0
CHANGELOG.json

@@ -5,2 +5,14 @@ {

{
"version": "0.5.0",
"tag": "@rushstack/worker-pool_v0.5.0",
"date": "Wed, 22 Jan 2025 03:03:47 GMT",
"comments": {
"minor": [
{
"comment": "Add a `workerResourceLimits` option to the `WorkerPool` constructor to control the available resources to the workers."
}
]
}
},
{
"version": "0.4.81",

@@ -7,0 +19,0 @@ "tag": "@rushstack/worker-pool_v0.4.81",

+8
-1
# Change Log - @rushstack/worker-pool
This log was last generated on Thu, 09 Jan 2025 01:10:10 GMT and should not be manually modified.
This log was last generated on Wed, 22 Jan 2025 03:03:47 GMT and should not be manually modified.
## 0.5.0
Wed, 22 Jan 2025 03:03:47 GMT
### Minor changes
- Add a `workerResourceLimits` option to the `WorkerPool` constructor to control the available resources to the workers.
## 0.4.81

@@ -6,0 +13,0 @@ Thu, 09 Jan 2025 01:10:10 GMT

+1
-1

@@ -8,5 +8,5 @@ // This file is read by tools that parse documentation comments conforming to the TSDoc standard.

"packageName": "@microsoft/api-extractor",
"packageVersion": "7.49.0"
"packageVersion": "7.49.1"
}
]
}

@@ -9,2 +9,3 @@ /**

import { ResourceLimits } from 'worker_threads';
import { Worker } from 'worker_threads';

@@ -41,2 +42,6 @@

workerScriptPath: string;
/**
* Optional resource limits for the workers.
*/
workerResourceLimits?: ResourceLimits;
}

@@ -69,2 +74,3 @@

private readonly _workerScript;
private readonly _workerResourceLimits;
constructor(options: IWorkerPoolOptions);

@@ -71,0 +77,0 @@ /**

/// <reference types="node" />
import { Worker } from 'worker_threads';
import { type ResourceLimits, Worker } from 'worker_threads';
/**

@@ -37,2 +37,6 @@ * Symbol to read the ID off of a worker

workerScriptPath: string;
/**
* Optional resource limits for the workers.
*/
workerResourceLimits?: ResourceLimits;
}

@@ -58,2 +62,3 @@ /**

private readonly _workerScript;
private readonly _workerResourceLimits;
constructor(options: IWorkerPoolOptions);

@@ -60,0 +65,0 @@ /**

@@ -1,1 +0,1 @@

{"version":3,"file":"WorkerPool.d.ts","sourceRoot":"","sources":["../src/WorkerPool.ts"],"names":[],"mappings":";AAGA,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAExC;;;GAGG;AACH,eAAO,MAAM,gBAAgB,EAAE,OAAO,MAA2B,CAAC;AAElE;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC;;OAEG;IACH,EAAE,EAAE,MAAM,CAAC;IACX;;OAEG;IACH,UAAU,EAAE,MAAM,CAAC;IACnB;;OAEG;IACH,iBAAiB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC/B;;OAEG;IACH,aAAa,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IACzC;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;OAEG;IACH,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED;;;;GAIG;AACH,qBAAa,UAAU;IACd,EAAE,EAAE,MAAM,CAAC;IACX,UAAU,EAAE,MAAM,CAAC;IAE1B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAW;IAClC,OAAO,CAAC,MAAM,CAAoB;IAClC,OAAO,CAAC,UAAU,CAAU;IAC5B,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAW;IACjC,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAyC;IACrE,OAAO,CAAC,QAAQ,CAAC,kBAAkB,CAA2B;IAC9D,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAuD;IAChF,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAyC;IAClE,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAU;IACtC,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAS;gBAEpB,OAAO,EAAE,kBAAkB;IAkB9C;;OAEG;IACI,cAAc,IAAI,MAAM;IAI/B;;OAEG;IACI,YAAY,IAAI,MAAM;IAI7B;;OAEG;IACI,YAAY,IAAI,MAAM;IAI7B;;;OAGG;IACU,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC;IAqBzC;;OAEG;IACI,KAAK,IAAI,IAAI;IAKpB;;;OAGG;IACI,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI;IAqB1C;;;OAGG;IACU,mBAAmB,CAAC,WAAW,EAAE,OAAO,GAAG,OAAO,CAAC,MAAM,CAAC;IAmBvE;;OAEG;IACH,OAAO,CAAC,aAAa;IAoCrB;;OAEG;IACH,OAAO,CAAC,cAAc;IAwBtB;;OAEG;IACH,OAAO,CAAC,QAAQ;CAWjB"}
{"version":3,"file":"WorkerPool.d.ts","sourceRoot":"","sources":["../src/WorkerPool.ts"],"names":[],"mappings":";AAGA,OAAO,EAAE,KAAK,cAAc,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAE7D;;;GAGG;AACH,eAAO,MAAM,gBAAgB,EAAE,OAAO,MAA2B,CAAC;AAElE;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC;;OAEG;IACH,EAAE,EAAE,MAAM,CAAC;IACX;;OAEG;IACH,UAAU,EAAE,MAAM,CAAC;IACnB;;OAEG;IACH,iBAAiB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC/B;;OAEG;IACH,aAAa,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IACzC;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;OAEG;IACH,gBAAgB,EAAE,MAAM,CAAC;IAEzB;;OAEG;IACH,oBAAoB,CAAC,EAAE,cAAc,CAAC;CACvC;AAED;;;;GAIG;AACH,qBAAa,UAAU;IACd,EAAE,EAAE,MAAM,CAAC;IACX,UAAU,EAAE,MAAM,CAAC;IAE1B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAW;IAClC,OAAO,CAAC,MAAM,CAAoB;IAClC,OAAO,CAAC,UAAU,CAAU;IAC5B,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAW;IACjC,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAyC;IACrE,OAAO,CAAC,QAAQ,CAAC,kBAAkB,CAA2B;IAC9D,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAuD;IAChF,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAyC;IAClE,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAU;IACtC,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAS;IACvC,OAAO,CAAC,QAAQ,CAAC,qBAAqB,CAA6B;gBAEhD,OAAO,EAAE,kBAAkB;IA2B9C;;OAEG;IACI,cAAc,IAAI,MAAM;IAI/B;;OAEG;IACI,YAAY,IAAI,MAAM;IAI7B;;OAEG;IACI,YAAY,IAAI,MAAM;IAI7B;;;OAGG;IACU,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC;IAqBzC;;OAEG;IACI,KAAK,IAAI,IAAI;IAKpB;;;OAGG;IACI,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI;IAqB1C;;;OAGG;IACU,mBAAmB,CAAC,WAAW,EAAE,OAAO,GAAG,OAAO,CAAC,MAAM,CAAC;IAmBvE;;OAEG;IACH,OAAO,CAAC,aAAa;IAqCrB;;OAEG;IACH,OAAO,CAAC,cAAc;IAwBtB;;OAEG;IACH,OAAO,CAAC,QAAQ;CAWjB"}

@@ -19,3 +19,3 @@ "use strict";

constructor(options) {
const { id, maxWorkers, onWorkerDestroyed, prepareWorker, workerData, workerScriptPath } = options;
const { id, maxWorkers, onWorkerDestroyed, prepareWorker, workerData, workerScriptPath, workerResourceLimits } = options;
this.id = id;

@@ -34,2 +34,3 @@ this.maxWorkers = maxWorkers;

this._workerScript = workerScriptPath;
this._workerResourceLimits = workerResourceLimits;
}

@@ -133,3 +134,4 @@ /**

eval: false,
workerData: this._workerData
workerData: this._workerData,
resourceLimits: this._workerResourceLimits
});

@@ -136,0 +138,0 @@ const id = `${this.id}#${++this._nextId}`;

@@ -1,1 +0,1 @@

{"version":3,"file":"WorkerPool.js","sourceRoot":"","sources":["../src/WorkerPool.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { Worker } from 'worker_threads';\n\n/**\n * Symbol to read the ID off of a worker\n * @internal\n */\nexport const WORKER_ID_SYMBOL: unique symbol = Symbol('workerId');\n\n/**\n * @internal\n */\nexport interface IWorkerPoolOptions {\n /**\n * Identifier for this pool, to assign to its workers for tracking\n */\n id: string;\n /**\n * Maximum number of concurrent workers this WorkerPool may spawn.\n */\n maxWorkers: number;\n /**\n * Optional callback invoked when a worker is destroyed.\n */\n onWorkerDestroyed?: () => void;\n /**\n * Optional callback invoked on a newly created worker.\n */\n prepareWorker?: (worker: Worker) => void;\n /**\n * Optional data to pass to workers when they are initialized.\n * Will be subjected to the Structured Clone algorithm.\n */\n workerData?: unknown;\n /**\n * Absolute path to the worker script.\n */\n workerScriptPath: string;\n}\n\n/**\n * Manages a pool of workers.\n * Workers will be shutdown by sending them the boolean value `false` in a postMessage.\n * @internal\n */\nexport class WorkerPool {\n public id: string;\n public maxWorkers: number;\n\n private readonly _alive: Worker[];\n private _error: Error | undefined;\n private _finishing: boolean;\n private readonly _idle: Worker[];\n private _nextId: number;\n private readonly _onComplete: [() => void, (error: Error) => void][];\n private readonly _onWorkerDestroyed: (() => void) | undefined;\n private readonly _pending: [(worker: Worker) => void, (error: Error) => void][];\n private readonly _prepare: ((worker: Worker) => void) | undefined;\n private readonly _workerData: unknown;\n private readonly _workerScript: string;\n\n public constructor(options: IWorkerPoolOptions) {\n const { id, maxWorkers, onWorkerDestroyed, prepareWorker, workerData, workerScriptPath } = options;\n\n this.id = id;\n this.maxWorkers = maxWorkers;\n this._alive = [];\n this._error = undefined;\n this._finishing = false;\n this._idle = [];\n this._nextId = 0;\n this._onComplete = [];\n this._onWorkerDestroyed = onWorkerDestroyed;\n this._pending = [];\n this._prepare = prepareWorker;\n this._workerData = workerData;\n this._workerScript = workerScriptPath;\n }\n\n /**\n * Gets the count of active workers.\n */\n public getActiveCount(): number {\n return this._alive.length - this._idle.length;\n }\n\n /**\n * Gets the count of idle workers.\n */\n public getIdleCount(): number {\n return this._idle.length;\n }\n\n /**\n * Gets the count of live workers.\n */\n public getLiveCount(): number {\n return this._alive.length;\n }\n\n /**\n * Tells the pool to shut down when all workers are done.\n * Returns a promise that will be fulfilled if all workers finish successfully, or reject with the first error.\n */\n public async finishAsync(): Promise<void> {\n this._finishing = true;\n\n if (this._error) {\n throw this._error;\n }\n\n if (!this._alive.length) {\n // The pool has no live workers, this is a no-op\n return;\n }\n\n // Clean up all idle workers\n for (const worker of this._idle.splice(0)) {\n worker.postMessage(false);\n }\n\n // There are still active workers, wait for them to clean up.\n await new Promise<void>((resolve, reject) => this._onComplete.push([resolve, reject]));\n }\n\n /**\n * Resets the pool and allows more work\n */\n public reset(): void {\n this._finishing = false;\n this._error = undefined;\n }\n\n /**\n * Returns a worker to the pool. If the pool is finishing, deallocates the worker.\n * @param worker - The worker to free\n */\n public checkinWorker(worker: Worker): void {\n if (this._error) {\n // Shut down the worker (failure)\n worker.postMessage(false);\n return;\n }\n\n const next: [(worker: Worker) => void, unknown] | undefined = this._pending.shift();\n\n if (next) {\n // Perform the next unit of work;\n next[0](worker);\n } else if (this._finishing) {\n // Shut down the worker (success)\n worker.postMessage(false);\n } else {\n // No pending work, idle the workers\n this._idle.push(worker);\n }\n }\n\n /**\n * Checks out a currently available worker or waits for the next free worker.\n * @param allowCreate - If creating new workers is allowed (subject to maxSize)\n */\n public async checkoutWorkerAsync(allowCreate: boolean): Promise<Worker> {\n if (this._error) {\n throw this._error;\n }\n\n let worker: Worker | undefined = this._idle.shift();\n if (!worker && allowCreate) {\n worker = this._createWorker();\n }\n\n if (worker) {\n return worker;\n }\n\n return await new Promise((resolve: (worker: Worker) => void, reject: (error: Error) => void) => {\n this._pending.push([resolve, reject]);\n });\n }\n\n /**\n * Creates a new worker if allowed by maxSize.\n */\n private _createWorker(): Worker | undefined {\n if (this._alive.length >= this.maxWorkers) {\n return;\n }\n\n const worker: Worker & {\n [WORKER_ID_SYMBOL]?: string;\n } = new Worker(this._workerScript, {\n eval: false,\n workerData: this._workerData\n });\n\n const id: string = `${this.id}#${++this._nextId}`;\n worker[WORKER_ID_SYMBOL] = id;\n\n this._alive.push(worker);\n\n worker.on('error', (err) => {\n this._onError(err);\n this._destroyWorker(worker);\n });\n\n worker.once('exit', (exitCode) => {\n if (exitCode !== 0) {\n this._onError(new Error(`Worker ${id} exited with code ${exitCode}`));\n }\n this._destroyWorker(worker);\n });\n\n if (this._prepare) {\n this._prepare(worker);\n }\n\n return worker;\n }\n\n /**\n * Cleans up a worker\n */\n private _destroyWorker(worker: Worker): void {\n const aliveIndex: number = this._alive.indexOf(worker);\n if (aliveIndex >= 0) {\n this._alive.splice(aliveIndex, 1);\n }\n\n const freeIndex: number = this._idle.indexOf(worker);\n if (freeIndex >= 0) {\n this._idle.splice(freeIndex, 1);\n }\n\n worker.unref();\n\n if (this._onWorkerDestroyed) {\n this._onWorkerDestroyed();\n }\n\n if (!this._alive.length && !this._error) {\n for (const [resolve] of this._onComplete.splice(0)) {\n resolve();\n }\n }\n }\n\n /**\n * Notifies all pending callbacks that an error has occurred and switches this pool into error state.\n */\n private _onError(error: Error): void {\n this._error = error;\n\n for (const [, reject] of this._pending.splice(0)) {\n reject(this._error);\n }\n\n for (const [, reject] of this._onComplete.splice(0)) {\n reject(this._error);\n }\n }\n}\n"]}
{"version":3,"file":"WorkerPool.js","sourceRoot":"","sources":["../src/WorkerPool.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { type ResourceLimits, Worker } from 'worker_threads';\n\n/**\n * Symbol to read the ID off of a worker\n * @internal\n */\nexport const WORKER_ID_SYMBOL: unique symbol = Symbol('workerId');\n\n/**\n * @internal\n */\nexport interface IWorkerPoolOptions {\n /**\n * Identifier for this pool, to assign to its workers for tracking\n */\n id: string;\n /**\n * Maximum number of concurrent workers this WorkerPool may spawn.\n */\n maxWorkers: number;\n /**\n * Optional callback invoked when a worker is destroyed.\n */\n onWorkerDestroyed?: () => void;\n /**\n * Optional callback invoked on a newly created worker.\n */\n prepareWorker?: (worker: Worker) => void;\n /**\n * Optional data to pass to workers when they are initialized.\n * Will be subjected to the Structured Clone algorithm.\n */\n workerData?: unknown;\n /**\n * Absolute path to the worker script.\n */\n workerScriptPath: string;\n\n /**\n * Optional resource limits for the workers.\n */\n workerResourceLimits?: ResourceLimits;\n}\n\n/**\n * Manages a pool of workers.\n * Workers will be shutdown by sending them the boolean value `false` in a postMessage.\n * @internal\n */\nexport class WorkerPool {\n public id: string;\n public maxWorkers: number;\n\n private readonly _alive: Worker[];\n private _error: Error | undefined;\n private _finishing: boolean;\n private readonly _idle: Worker[];\n private _nextId: number;\n private readonly _onComplete: [() => void, (error: Error) => void][];\n private readonly _onWorkerDestroyed: (() => void) | undefined;\n private readonly _pending: [(worker: Worker) => void, (error: Error) => void][];\n private readonly _prepare: ((worker: Worker) => void) | undefined;\n private readonly _workerData: unknown;\n private readonly _workerScript: string;\n private readonly _workerResourceLimits: ResourceLimits | undefined;\n\n public constructor(options: IWorkerPoolOptions) {\n const {\n id,\n maxWorkers,\n onWorkerDestroyed,\n prepareWorker,\n workerData,\n workerScriptPath,\n workerResourceLimits\n } = options;\n\n this.id = id;\n this.maxWorkers = maxWorkers;\n this._alive = [];\n this._error = undefined;\n this._finishing = false;\n this._idle = [];\n this._nextId = 0;\n this._onComplete = [];\n this._onWorkerDestroyed = onWorkerDestroyed;\n this._pending = [];\n this._prepare = prepareWorker;\n this._workerData = workerData;\n this._workerScript = workerScriptPath;\n this._workerResourceLimits = workerResourceLimits;\n }\n\n /**\n * Gets the count of active workers.\n */\n public getActiveCount(): number {\n return this._alive.length - this._idle.length;\n }\n\n /**\n * Gets the count of idle workers.\n */\n public getIdleCount(): number {\n return this._idle.length;\n }\n\n /**\n * Gets the count of live workers.\n */\n public getLiveCount(): number {\n return this._alive.length;\n }\n\n /**\n * Tells the pool to shut down when all workers are done.\n * Returns a promise that will be fulfilled if all workers finish successfully, or reject with the first error.\n */\n public async finishAsync(): Promise<void> {\n this._finishing = true;\n\n if (this._error) {\n throw this._error;\n }\n\n if (!this._alive.length) {\n // The pool has no live workers, this is a no-op\n return;\n }\n\n // Clean up all idle workers\n for (const worker of this._idle.splice(0)) {\n worker.postMessage(false);\n }\n\n // There are still active workers, wait for them to clean up.\n await new Promise<void>((resolve, reject) => this._onComplete.push([resolve, reject]));\n }\n\n /**\n * Resets the pool and allows more work\n */\n public reset(): void {\n this._finishing = false;\n this._error = undefined;\n }\n\n /**\n * Returns a worker to the pool. If the pool is finishing, deallocates the worker.\n * @param worker - The worker to free\n */\n public checkinWorker(worker: Worker): void {\n if (this._error) {\n // Shut down the worker (failure)\n worker.postMessage(false);\n return;\n }\n\n const next: [(worker: Worker) => void, unknown] | undefined = this._pending.shift();\n\n if (next) {\n // Perform the next unit of work;\n next[0](worker);\n } else if (this._finishing) {\n // Shut down the worker (success)\n worker.postMessage(false);\n } else {\n // No pending work, idle the workers\n this._idle.push(worker);\n }\n }\n\n /**\n * Checks out a currently available worker or waits for the next free worker.\n * @param allowCreate - If creating new workers is allowed (subject to maxSize)\n */\n public async checkoutWorkerAsync(allowCreate: boolean): Promise<Worker> {\n if (this._error) {\n throw this._error;\n }\n\n let worker: Worker | undefined = this._idle.shift();\n if (!worker && allowCreate) {\n worker = this._createWorker();\n }\n\n if (worker) {\n return worker;\n }\n\n return await new Promise((resolve: (worker: Worker) => void, reject: (error: Error) => void) => {\n this._pending.push([resolve, reject]);\n });\n }\n\n /**\n * Creates a new worker if allowed by maxSize.\n */\n private _createWorker(): Worker | undefined {\n if (this._alive.length >= this.maxWorkers) {\n return;\n }\n\n const worker: Worker & {\n [WORKER_ID_SYMBOL]?: string;\n } = new Worker(this._workerScript, {\n eval: false,\n workerData: this._workerData,\n resourceLimits: this._workerResourceLimits\n });\n\n const id: string = `${this.id}#${++this._nextId}`;\n worker[WORKER_ID_SYMBOL] = id;\n\n this._alive.push(worker);\n\n worker.on('error', (err) => {\n this._onError(err);\n this._destroyWorker(worker);\n });\n\n worker.once('exit', (exitCode) => {\n if (exitCode !== 0) {\n this._onError(new Error(`Worker ${id} exited with code ${exitCode}`));\n }\n this._destroyWorker(worker);\n });\n\n if (this._prepare) {\n this._prepare(worker);\n }\n\n return worker;\n }\n\n /**\n * Cleans up a worker\n */\n private _destroyWorker(worker: Worker): void {\n const aliveIndex: number = this._alive.indexOf(worker);\n if (aliveIndex >= 0) {\n this._alive.splice(aliveIndex, 1);\n }\n\n const freeIndex: number = this._idle.indexOf(worker);\n if (freeIndex >= 0) {\n this._idle.splice(freeIndex, 1);\n }\n\n worker.unref();\n\n if (this._onWorkerDestroyed) {\n this._onWorkerDestroyed();\n }\n\n if (!this._alive.length && !this._error) {\n for (const [resolve] of this._onComplete.splice(0)) {\n resolve();\n }\n }\n }\n\n /**\n * Notifies all pending callbacks that an error has occurred and switches this pool into error state.\n */\n private _onError(error: Error): void {\n this._error = error;\n\n for (const [, reject] of this._pending.splice(0)) {\n reject(this._error);\n }\n\n for (const [, reject] of this._onComplete.splice(0)) {\n reject(this._error);\n }\n }\n}\n"]}
{
"name": "@rushstack/worker-pool",
"version": "0.4.81",
"version": "0.5.0",
"description": "Lightweight worker pool using NodeJS worker_threads",

@@ -5,0 +5,0 @@ "main": "lib/index.js",