Comparing version 1.2.0 to 1.5.0
@@ -5,2 +5,3 @@ import { FN, PromiseValue, Methods, MethodsSerialized, Options, Task } from './types'; | ||
terminated: boolean; | ||
timeout: number; | ||
name: string; | ||
@@ -7,0 +8,0 @@ size: number; |
@@ -9,6 +9,7 @@ "use strict"; | ||
constructor(options) { | ||
var _a, _b; | ||
var _a, _b, _c; | ||
this.terminated = false; | ||
this.name = (_a = options.name) !== null && _a !== void 0 ? _a : 'WorkTank-Worker'; | ||
this.size = (_b = options.size) !== null && _b !== void 0 ? _b : 1; | ||
this.timeout = (_a = options.timeout) !== null && _a !== void 0 ? _a : Infinity; | ||
this.name = (_b = options.name) !== null && _b !== void 0 ? _b : 'WorkTank-Worker'; | ||
this.size = (_c = options.size) !== null && _c !== void 0 ? _c : 1; | ||
this.methods = this._getMethodsSerialized(options.methods); | ||
@@ -90,7 +91,19 @@ this.tasksBusy = new Set(); | ||
this.tasksBusy.add(task); | ||
let timeoutId; | ||
if (this.timeout > 0 && this.timeout !== Infinity) { | ||
const timeout = Math.min(2147483647, this.timeout); | ||
timeoutId = setTimeout(() => { | ||
worker.terminate(); | ||
}, timeout); | ||
} | ||
task.promise.finally(() => { | ||
if (timeoutId) { | ||
clearTimeout(timeoutId); | ||
} | ||
if (this.terminated) | ||
return; | ||
this.workersBusy.delete(worker); | ||
this.workersReady.add(worker); | ||
if (!worker.terminated) { | ||
this.workersReady.add(worker); | ||
} | ||
this.tasksBusy.delete(task); | ||
@@ -97,0 +110,0 @@ this.tick(); |
@@ -37,2 +37,3 @@ declare type FN = (...args: any[]) => any; | ||
size?: number; | ||
timeout?: number; | ||
methods: Methods<MethodName, MethodFunction> | string; | ||
@@ -39,0 +40,0 @@ }; |
@@ -1,2 +0,2 @@ | ||
declare const _default: "(()=>{const i=(()=>{const e=typeof postMessage==\"function\";if(e){const t=globalThis;return{on:(n,r)=>{t.addEventListener(n,d=>{r(d.data)})},send:n=>{t.postMessage(n)}}}else{const t=require(\"worker_threads\").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{const n=o.methods[e],r={require:globalThis.require},d=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:\"result\",value:s})}catch(c){a(c)}},a=s=>{s=s instanceof Error?s:typeof s==\"string\"?new Error(s):new Error;const{message:c,name:u,stack:p}=s;i.send({type:\"result\",error:{message:c,name:u,stack:p}})};d.then(g,a)},init:e=>{o.register(e),i.send({type:\"ready\"})},message:e=>{if(e.type===\"init\")return o.init(e.methods);if(e.type===\"exec\")return o.exec(e.method,e.args)},register:e=>{if(typeof e==\"string\"){const t=new Function(e)();for(const n in t)o.methods[n]=t[n]}else for(const t in e){const n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on(\"message\",o.message);})();"; | ||
declare const _default: "(()=>{var f=(e=>typeof require!=\"undefined\"?require:typeof Proxy!=\"undefined\"?new Proxy(e,{get:(t,n)=>(typeof require!=\"undefined\"?require:t)[n]}):e)(function(e){if(typeof require!=\"undefined\")return require.apply(this,arguments);throw new Error('Dynamic require of \"'+e+'\" is not supported')});var i=(()=>{if(typeof postMessage==\"function\"){let t=globalThis;return{on:(n,r)=>{t.addEventListener(n,c=>{r(c.data)})},send:n=>{t.postMessage(n)}}}else{let t=f(\"worker_threads\").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{let n=o.methods[e],r={require:globalThis.require},c=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:\"result\",value:s})}catch(d){a(d)}},a=s=>{s=s instanceof Error?s:typeof s==\"string\"?new Error(s):new Error;let{message:d,name:u,stack:p}=s;i.send({type:\"result\",error:{message:d,name:u,stack:p}})};c.then(g,a)},init:e=>{o.register(e),i.send({type:\"ready\"})},message:e=>{if(e.type===\"init\")return o.init(e.methods);if(e.type===\"exec\")return o.exec(e.method,e.args)},register:e=>{if(typeof e==\"string\"){let t=new Function(e)();for(let n in t)o.methods[n]=t[n]}else for(let t in e){let n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on(\"message\",o.message);})();"; | ||
export default _default; |
"use strict"; | ||
/* COMPILED WORKER */ | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
exports.default = '(()=>{const i=(()=>{const e=typeof postMessage=="function";if(e){const t=globalThis;return{on:(n,r)=>{t.addEventListener(n,d=>{r(d.data)})},send:n=>{t.postMessage(n)}}}else{const t=require("worker_threads").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{const n=o.methods[e],r={require:globalThis.require},d=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:"result",value:s})}catch(c){a(c)}},a=s=>{s=s instanceof Error?s:typeof s=="string"?new Error(s):new Error;const{message:c,name:u,stack:p}=s;i.send({type:"result",error:{message:c,name:u,stack:p}})};d.then(g,a)},init:e=>{o.register(e),i.send({type:"ready"})},message:e=>{if(e.type==="init")return o.init(e.methods);if(e.type==="exec")return o.exec(e.method,e.args)},register:e=>{if(typeof e=="string"){const t=new Function(e)();for(const n in t)o.methods[n]=t[n]}else for(const t in e){const n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on("message",o.message);})();'; | ||
exports.default = '(()=>{var f=(e=>typeof require!="undefined"?require:typeof Proxy!="undefined"?new Proxy(e,{get:(t,n)=>(typeof require!="undefined"?require:t)[n]}):e)(function(e){if(typeof require!="undefined")return require.apply(this,arguments);throw new Error(\'Dynamic require of "\'+e+\'" is not supported\')});var i=(()=>{if(typeof postMessage=="function"){let t=globalThis;return{on:(n,r)=>{t.addEventListener(n,c=>{r(c.data)})},send:n=>{t.postMessage(n)}}}else{let t=f("worker_threads").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{let n=o.methods[e],r={require:globalThis.require},c=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:"result",value:s})}catch(d){a(d)}},a=s=>{s=s instanceof Error?s:typeof s=="string"?new Error(s):new Error;let{message:d,name:u,stack:p}=s;i.send({type:"result",error:{message:d,name:u,stack:p}})};c.then(g,a)},init:e=>{o.register(e),i.send({type:"ready"})},message:e=>{if(e.type==="init")return o.init(e.methods);if(e.type==="exec")return o.exec(e.method,e.args)},register:e=>{if(typeof e=="string"){let t=new Function(e)();for(let n in t)o.methods[n]=t[n]}else for(let t in e){let n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on("message",o.message);})();'; |
@@ -57,2 +57,6 @@ "use strict"; | ||
this.worker.terminate(); | ||
if (this.task) { | ||
const error = new Error(`WorkTank Worker (${this.name}): terminated`); | ||
this.task.reject(error); | ||
} | ||
} | ||
@@ -59,0 +63,0 @@ tick() { |
{ | ||
"name": "worktank", | ||
"description": "A simple isomorphic library for executing functions inside WebWorkers or Node Threads pools.", | ||
"version": "1.2.0", | ||
"version": "1.5.0", | ||
"main": "dist/index.js", | ||
@@ -43,3 +43,3 @@ "types": "dist/index.d.ts", | ||
"devDependencies": { | ||
"@types/node": "^12.20.6", | ||
"@types/node": "^16.11.12", | ||
"rimraf": "^3.0.0", | ||
@@ -46,0 +46,0 @@ "typescript": "^3.5.3", |
@@ -36,2 +36,3 @@ # WorkTank | ||
size: 5, // The maximum number of worker threads to spawn, they will only get spawned if actually needed | ||
timeout: 10000, // The maximum number of milliseconds to wait for the result from the worker, if exceeded the worker is terminated and the execution promise rejects | ||
methods: { // An object mapping function names to functions objects to serialize and deserialize into each worker thread, only functions that don't depend on their closure can be serialized | ||
@@ -38,0 +39,0 @@ sum: function ( a: number, b: number ): number { |
@@ -15,2 +15,3 @@ | ||
terminated: boolean; | ||
timeout: number; | ||
name: string; | ||
@@ -29,2 +30,3 @@ size: number; | ||
this.terminated = false; | ||
this.timeout = options.timeout ?? Infinity; | ||
this.name = options.name ?? 'WorkTank-Worker'; | ||
@@ -152,9 +154,34 @@ this.size = options.size ?? 1; | ||
let timeoutId: NodeJS.Timeout; | ||
if ( this.timeout > 0 && this.timeout !== Infinity ) { | ||
const timeout = Math.min ( 2147483647, this.timeout ); | ||
timeoutId = setTimeout ( (): void => { | ||
worker.terminate (); | ||
}, timeout ); | ||
} | ||
task.promise.finally ( () => { | ||
if ( timeoutId ) { | ||
clearTimeout ( timeoutId ); | ||
} | ||
if ( this.terminated ) return; | ||
this.workersBusy.delete ( worker ); | ||
this.workersReady.add ( worker ); | ||
if ( !worker.terminated ) { | ||
this.workersReady.add ( worker ); | ||
} | ||
this.tasksBusy.delete ( task ); | ||
@@ -161,0 +188,0 @@ |
@@ -52,2 +52,3 @@ | ||
size?: number, | ||
timeout?: number, | ||
methods: Methods<MethodName, MethodFunction> | string | ||
@@ -54,0 +55,0 @@ }; |
/* COMPILED WORKER */ | ||
export default '(()=>{const i=(()=>{const e=typeof postMessage=="function";if(e){const t=globalThis;return{on:(n,r)=>{t.addEventListener(n,d=>{r(d.data)})},send:n=>{t.postMessage(n)}}}else{const t=require("worker_threads").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{const n=o.methods[e],r={require:globalThis.require},d=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:"result",value:s})}catch(c){a(c)}},a=s=>{s=s instanceof Error?s:typeof s=="string"?new Error(s):new Error;const{message:c,name:u,stack:p}=s;i.send({type:"result",error:{message:c,name:u,stack:p}})};d.then(g,a)},init:e=>{o.register(e),i.send({type:"ready"})},message:e=>{if(e.type==="init")return o.init(e.methods);if(e.type==="exec")return o.exec(e.method,e.args)},register:e=>{if(typeof e=="string"){const t=new Function(e)();for(const n in t)o.methods[n]=t[n]}else for(const t in e){const n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on("message",o.message);})();'; | ||
export default '(()=>{var f=(e=>typeof require!="undefined"?require:typeof Proxy!="undefined"?new Proxy(e,{get:(t,n)=>(typeof require!="undefined"?require:t)[n]}):e)(function(e){if(typeof require!="undefined")return require.apply(this,arguments);throw new Error(\'Dynamic require of "\'+e+\'" is not supported\')});var i=(()=>{if(typeof postMessage=="function"){let t=globalThis;return{on:(n,r)=>{t.addEventListener(n,c=>{r(c.data)})},send:n=>{t.postMessage(n)}}}else{let t=f("worker_threads").parentPort;return{on:(n,r)=>{t.on(n,r)},send:n=>{t.postMessage(n)}}}})(),o={methods:{},exec:(e,t)=>{let n=o.methods[e],r={require:globalThis.require},c=new Promise(s=>s(n.apply(r,t))),g=s=>{try{i.send({type:"result",value:s})}catch(d){a(d)}},a=s=>{s=s instanceof Error?s:typeof s=="string"?new Error(s):new Error;let{message:d,name:u,stack:p}=s;i.send({type:"result",error:{message:d,name:u,stack:p}})};c.then(g,a)},init:e=>{o.register(e),i.send({type:"ready"})},message:e=>{if(e.type==="init")return o.init(e.methods);if(e.type==="exec")return o.exec(e.method,e.args)},register:e=>{if(typeof e=="string"){let t=new Function(e)();for(let n in t)o.methods[n]=t[n]}else for(let t in e){let n=new Function(`return (${e[t]})`)();o.methods[t]=n}}};i.on("message",o.message);})();'; |
@@ -106,2 +106,10 @@ | ||
if ( this.task ) { | ||
const error = new Error ( `WorkTank Worker (${this.name}): terminated` ); | ||
this.task.reject ( error ); | ||
} | ||
} | ||
@@ -108,0 +116,0 @@ |
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
40106
876
80