@xylabs/threads 4.4.35 → 4.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/enum.d.ts ADDED
@@ -0,0 +1,5 @@
1
+ export declare const Enum: <const T extends Record<string | number | symbol, unknown>>(obj: Readonly<T>) => Enum<T>;
2
+ export type Enum<T extends Readonly<Record<string | number | symbol, unknown>>> = {
3
+ readonly [K in keyof T]: T[K];
4
+ };
5
+ export type EnumValue<T extends Record<string | number | symbol, unknown>, K = Enum<T>> = K[keyof K];
package/dist/enum.js ADDED
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Enum = void 0;
4
+ const Enum = (obj) => {
5
+ return obj;
6
+ };
7
+ exports.Enum = Enum;
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Enum = void 0;
4
+ const Enum = (obj) => {
5
+ return obj;
6
+ };
7
+ exports.Enum = Enum;
@@ -1,14 +1,14 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.PoolEventType = void 0;
4
- var PoolEventType;
5
- (function (PoolEventType) {
6
- PoolEventType["initialized"] = "initialized";
7
- PoolEventType["taskCanceled"] = "taskCanceled";
8
- PoolEventType["taskCompleted"] = "taskCompleted";
9
- PoolEventType["taskFailed"] = "taskFailed";
10
- PoolEventType["taskQueued"] = "taskQueued";
11
- PoolEventType["taskQueueDrained"] = "taskQueueDrained";
12
- PoolEventType["taskStart"] = "taskStart";
13
- PoolEventType["terminated"] = "terminated";
14
- })(PoolEventType || (exports.PoolEventType = PoolEventType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.PoolEventType = (0, enum_1.Enum)({
6
+ initialized: 'initialized',
7
+ taskCanceled: 'taskCanceled',
8
+ taskCompleted: 'taskCompleted',
9
+ taskFailed: 'taskFailed',
10
+ taskQueued: 'taskQueued',
11
+ taskQueueDrained: 'taskQueueDrained',
12
+ taskStart: 'taskStart',
13
+ terminated: 'terminated',
14
+ });
@@ -6,7 +6,6 @@ Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.Thread = exports.PoolEventType = exports.Pool = void 0;
7
7
  const debug_1 = __importDefault(require("debug"));
8
8
  const observable_fns_1 = require("observable-fns");
9
- const ponyfills_1 = require("../ponyfills");
10
9
  const implementation_1 = require("./implementation");
11
10
  const pool_types_1 = require("./pool-types");
12
11
  const thread_1 = require("./thread");
@@ -121,7 +120,10 @@ class WorkerPool {
121
120
  this.eventSubject.next({ type: pool_types_1.PoolEventType.taskQueueDrained });
122
121
  return;
123
122
  }
124
- this.run(availableWorker, nextTask);
123
+ this.run(availableWorker, nextTask).catch((error) => {
124
+ this.debug('Error while running task:', error);
125
+ this.eventSubject.error(error);
126
+ });
125
127
  }
126
128
  taskCompletion(taskID) {
127
129
  return new Promise((resolve, reject) => {
@@ -153,7 +155,7 @@ class WorkerPool {
153
155
  throw this.initErrors[0];
154
156
  }
155
157
  if (allowResolvingImmediately && this.taskQueue.length === 0) {
156
- await (0, ponyfills_1.allSettled)(getCurrentlyRunningTasks());
158
+ await Promise.allSettled(getCurrentlyRunningTasks());
157
159
  return taskFailures;
158
160
  }
159
161
  await new Promise((resolve, reject) => {
@@ -167,7 +169,7 @@ class WorkerPool {
167
169
  },
168
170
  });
169
171
  });
170
- await (0, ponyfills_1.allSettled)(getCurrentlyRunningTasks());
172
+ await Promise.allSettled(getCurrentlyRunningTasks());
171
173
  failureSubscription.unsubscribe();
172
174
  return taskFailures;
173
175
  }
@@ -1,9 +1,9 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.WorkerEventType = void 0;
4
- var WorkerEventType;
5
- (function (WorkerEventType) {
6
- WorkerEventType["internalError"] = "internalError";
7
- WorkerEventType["message"] = "message";
8
- WorkerEventType["termination"] = "termination";
9
- })(WorkerEventType || (exports.WorkerEventType = WorkerEventType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.WorkerEventType = (0, enum_1.Enum)({
6
+ internalError: 'internalError',
7
+ message: 'message',
8
+ termination: 'termination',
9
+ });
@@ -1,16 +1,15 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.WorkerMessageType = exports.MasterMessageType = void 0;
4
- var MasterMessageType;
5
- (function (MasterMessageType) {
6
- MasterMessageType["cancel"] = "cancel";
7
- MasterMessageType["run"] = "run";
8
- })(MasterMessageType || (exports.MasterMessageType = MasterMessageType = {}));
9
- var WorkerMessageType;
10
- (function (WorkerMessageType) {
11
- WorkerMessageType["error"] = "error";
12
- WorkerMessageType["init"] = "init";
13
- WorkerMessageType["result"] = "result";
14
- WorkerMessageType["running"] = "running";
15
- WorkerMessageType["uncaughtError"] = "uncaughtError";
16
- })(WorkerMessageType || (exports.WorkerMessageType = WorkerMessageType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.MasterMessageType = (0, enum_1.Enum)({
6
+ cancel: 'cancel',
7
+ run: 'run',
8
+ });
9
+ exports.WorkerMessageType = (0, enum_1.Enum)({
10
+ error: 'error',
11
+ init: 'init',
12
+ result: 'result',
13
+ running: 'running',
14
+ uncaughtError: 'uncaughtError',
15
+ });
@@ -1,42 +1,45 @@
1
+ import type { EnumValue } from '../enum';
2
+ import { Enum } from '../enum';
1
3
  import type { Thread } from './thread';
2
- export declare enum PoolEventType {
3
- initialized = "initialized",
4
- taskCanceled = "taskCanceled",
5
- taskCompleted = "taskCompleted",
6
- taskFailed = "taskFailed",
7
- taskQueued = "taskQueued",
8
- taskQueueDrained = "taskQueueDrained",
9
- taskStart = "taskStart",
10
- terminated = "terminated"
11
- }
4
+ export declare const PoolEventType: Enum<{
5
+ initialized: "initialized";
6
+ taskCanceled: "taskCanceled";
7
+ taskCompleted: "taskCompleted";
8
+ taskFailed: "taskFailed";
9
+ taskQueued: "taskQueued";
10
+ taskQueueDrained: "taskQueueDrained";
11
+ taskStart: "taskStart";
12
+ terminated: "terminated";
13
+ }>;
14
+ export type PoolEventType = EnumValue<typeof PoolEventType>;
12
15
  export type TaskRunFunction<ThreadType extends Thread, Return> = (worker: ThreadType) => Promise<Return>;
13
16
  export type PoolEvent<ThreadType extends Thread> = {
14
- type: PoolEventType.initialized;
17
+ type: 'initialized';
15
18
  size: number;
16
19
  } | {
17
- type: PoolEventType.taskQueued;
20
+ type: 'taskQueued';
18
21
  taskID: number;
19
22
  } | {
20
- type: PoolEventType.taskQueueDrained;
23
+ type: 'taskQueueDrained';
21
24
  } | {
22
- type: PoolEventType.taskStart;
25
+ type: 'taskStart';
23
26
  taskID: number;
24
27
  workerID: number;
25
28
  } | {
26
- type: PoolEventType.taskCompleted;
29
+ type: 'taskCompleted';
27
30
  returnValue: any;
28
31
  taskID: number;
29
32
  workerID: number;
30
33
  } | {
31
- type: PoolEventType.taskFailed;
34
+ type: 'taskFailed';
32
35
  error: Error;
33
36
  taskID: number;
34
37
  workerID: number;
35
38
  } | {
36
- type: PoolEventType.taskCanceled;
39
+ type: 'taskCanceled';
37
40
  taskID: number;
38
41
  } | {
39
- type: PoolEventType.terminated;
42
+ type: 'terminated';
40
43
  remainingQueue: Array<QueuedTask<ThreadType, any>>;
41
44
  };
42
45
  export interface WorkerDescriptor<ThreadType extends Thread> {
@@ -1,14 +1,14 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.PoolEventType = void 0;
4
- var PoolEventType;
5
- (function (PoolEventType) {
6
- PoolEventType["initialized"] = "initialized";
7
- PoolEventType["taskCanceled"] = "taskCanceled";
8
- PoolEventType["taskCompleted"] = "taskCompleted";
9
- PoolEventType["taskFailed"] = "taskFailed";
10
- PoolEventType["taskQueued"] = "taskQueued";
11
- PoolEventType["taskQueueDrained"] = "taskQueueDrained";
12
- PoolEventType["taskStart"] = "taskStart";
13
- PoolEventType["terminated"] = "terminated";
14
- })(PoolEventType || (exports.PoolEventType = PoolEventType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.PoolEventType = (0, enum_1.Enum)({
6
+ initialized: 'initialized',
7
+ taskCanceled: 'taskCanceled',
8
+ taskCompleted: 'taskCompleted',
9
+ taskFailed: 'taskFailed',
10
+ taskQueued: 'taskQueued',
11
+ taskQueueDrained: 'taskQueueDrained',
12
+ taskStart: 'taskStart',
13
+ terminated: 'terminated',
14
+ });
@@ -20,7 +20,16 @@ interface PoolOptions {
20
20
  size?: number;
21
21
  }
22
22
  declare class WorkerPool<ThreadType extends Thread> implements Pool<ThreadType> {
23
- static EventType: typeof PoolEventType;
23
+ static EventType: import("../enum").Enum<{
24
+ initialized: "initialized";
25
+ taskCanceled: "taskCanceled";
26
+ taskCompleted: "taskCompleted";
27
+ taskFailed: "taskFailed";
28
+ taskQueued: "taskQueued";
29
+ taskQueueDrained: "taskQueueDrained";
30
+ taskStart: "taskStart";
31
+ terminated: "terminated";
32
+ }>;
24
33
  private readonly debug;
25
34
  private readonly eventObservable;
26
35
  private readonly options;
@@ -6,7 +6,6 @@ Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.Thread = exports.PoolEventType = exports.Pool = void 0;
7
7
  const debug_1 = __importDefault(require("debug"));
8
8
  const observable_fns_1 = require("observable-fns");
9
- const ponyfills_1 = require("../ponyfills");
10
9
  const implementation_1 = require("./implementation");
11
10
  const pool_types_1 = require("./pool-types");
12
11
  const thread_1 = require("./thread");
@@ -121,7 +120,10 @@ class WorkerPool {
121
120
  this.eventSubject.next({ type: pool_types_1.PoolEventType.taskQueueDrained });
122
121
  return;
123
122
  }
124
- this.run(availableWorker, nextTask);
123
+ this.run(availableWorker, nextTask).catch((error) => {
124
+ this.debug('Error while running task:', error);
125
+ this.eventSubject.error(error);
126
+ });
125
127
  }
126
128
  taskCompletion(taskID) {
127
129
  return new Promise((resolve, reject) => {
@@ -153,7 +155,7 @@ class WorkerPool {
153
155
  throw this.initErrors[0];
154
156
  }
155
157
  if (allowResolvingImmediately && this.taskQueue.length === 0) {
156
- await (0, ponyfills_1.allSettled)(getCurrentlyRunningTasks());
158
+ await Promise.allSettled(getCurrentlyRunningTasks());
157
159
  return taskFailures;
158
160
  }
159
161
  await new Promise((resolve, reject) => {
@@ -167,7 +169,7 @@ class WorkerPool {
167
169
  },
168
170
  });
169
171
  });
170
- await (0, ponyfills_1.allSettled)(getCurrentlyRunningTasks());
172
+ await Promise.allSettled(getCurrentlyRunningTasks());
171
173
  failureSubscription.unsubscribe();
172
174
  return taskFailures;
173
175
  }
@@ -1,4 +1,6 @@
1
1
  import type { Observable } from 'observable-fns';
2
+ import type { EnumValue } from '../enum';
3
+ import { Enum } from '../enum';
2
4
  import type { ObservablePromise } from '../observable-promise';
3
5
  import type { $errors, $events, $terminate, $worker } from '../symbols';
4
6
  import type { TransferDescriptor } from '../transferable';
@@ -37,9 +39,8 @@ interface AnyFunctionThread extends PrivateThreadProps {
37
39
  interface AnyModuleThread extends PrivateThreadProps {
38
40
  }
39
41
  export type Thread = AnyFunctionThread | AnyModuleThread;
40
- export type TransferList = Transferable[];
41
42
  export interface Worker extends EventTarget {
42
- postMessage(value: any, transferList?: TransferList): void;
43
+ postMessage(value: any, transferList?: Transferable[]): void;
43
44
  terminate(callback?: (error?: Error, exitCode?: number) => void): void | Promise<number>;
44
45
  }
45
46
  export interface ThreadsWorkerOptions extends WorkerOptions {
@@ -54,7 +55,7 @@ export interface ThreadsWorkerOptions extends WorkerOptions {
54
55
  }
55
56
  export declare class WorkerImplementation extends EventTarget implements Worker {
56
57
  constructor(path: string, options?: ThreadsWorkerOptions);
57
- postMessage(value: any, transferList?: TransferList): void;
58
+ postMessage(value: any, transferList?: Transferable[]): void;
58
59
  terminate(): void | Promise<number>;
59
60
  }
60
61
  export declare class BlobWorker extends WorkerImplementation {
@@ -65,21 +66,22 @@ export interface ImplementationExport {
65
66
  blob: typeof BlobWorker;
66
67
  default: typeof WorkerImplementation;
67
68
  }
68
- export declare enum WorkerEventType {
69
- internalError = "internalError",
70
- message = "message",
71
- termination = "termination"
72
- }
69
+ export declare const WorkerEventType: Enum<{
70
+ internalError: "internalError";
71
+ message: "message";
72
+ termination: "termination";
73
+ }>;
74
+ export type WorkerEventType = EnumValue<typeof WorkerEventType>;
73
75
  export interface WorkerInternalErrorEvent {
74
76
  error: Error;
75
- type: WorkerEventType.internalError;
77
+ type: 'internalError';
76
78
  }
77
79
  export interface WorkerMessageEvent<Data> {
78
80
  data: Data;
79
- type: WorkerEventType.message;
81
+ type: 'message';
80
82
  }
81
83
  export interface WorkerTerminationEvent {
82
- type: WorkerEventType.termination;
84
+ type: 'termination';
83
85
  }
84
86
  export type WorkerEvent = WorkerInternalErrorEvent | WorkerMessageEvent<any> | WorkerTerminationEvent;
85
87
  export {};
@@ -1,9 +1,9 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.WorkerEventType = void 0;
4
- var WorkerEventType;
5
- (function (WorkerEventType) {
6
- WorkerEventType["internalError"] = "internalError";
7
- WorkerEventType["message"] = "message";
8
- WorkerEventType["termination"] = "termination";
9
- })(WorkerEventType || (exports.WorkerEventType = WorkerEventType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.WorkerEventType = (0, enum_1.Enum)({
6
+ internalError: 'internalError',
7
+ message: 'message',
8
+ termination: 'termination',
9
+ });
@@ -1,32 +1,36 @@
1
+ import type { EnumValue } from '../enum';
2
+ import { Enum } from '../enum';
1
3
  export interface SerializedError {
2
4
  __error_marker: '$$error';
3
5
  message: string;
4
6
  name: string;
5
7
  stack?: string;
6
8
  }
7
- export declare enum MasterMessageType {
8
- cancel = "cancel",
9
- run = "run"
10
- }
9
+ export declare const MasterMessageType: Enum<{
10
+ cancel: "cancel";
11
+ run: "run";
12
+ }>;
13
+ export type MasterMessageType = EnumValue<typeof MasterMessageType>;
11
14
  export type MasterJobCancelMessage = {
12
- type: MasterMessageType.cancel;
15
+ type: 'cancel';
13
16
  uid: number;
14
17
  };
15
18
  export type MasterJobRunMessage = {
16
- type: MasterMessageType.run;
19
+ type: 'run';
17
20
  uid: number;
18
21
  method?: string;
19
22
  args: any[];
20
23
  };
21
- export declare enum WorkerMessageType {
22
- error = "error",
23
- init = "init",
24
- result = "result",
25
- running = "running",
26
- uncaughtError = "uncaughtError"
27
- }
24
+ export declare const WorkerMessageType: Enum<{
25
+ error: "error";
26
+ init: "init";
27
+ result: "result";
28
+ running: "running";
29
+ uncaughtError: "uncaughtError";
30
+ }>;
31
+ export type WorkerMessageType = EnumValue<typeof WorkerMessageType>;
28
32
  export type WorkerUncaughtErrorMessage = {
29
- type: WorkerMessageType.uncaughtError;
33
+ type: 'uncaughtError';
30
34
  error: {
31
35
  message: string;
32
36
  name: string;
@@ -34,7 +38,7 @@ export type WorkerUncaughtErrorMessage = {
34
38
  };
35
39
  };
36
40
  export type WorkerInitMessage = {
37
- type: WorkerMessageType.init;
41
+ type: 'init';
38
42
  exposed: {
39
43
  type: 'function';
40
44
  } | {
@@ -43,18 +47,18 @@ export type WorkerInitMessage = {
43
47
  };
44
48
  };
45
49
  export type WorkerJobErrorMessage = {
46
- type: WorkerMessageType.error;
50
+ type: 'error';
47
51
  uid: number;
48
52
  error: SerializedError;
49
53
  };
50
54
  export type WorkerJobResultMessage = {
51
- type: WorkerMessageType.result;
55
+ type: 'result';
52
56
  uid: number;
53
57
  complete?: true;
54
58
  payload?: any;
55
59
  };
56
60
  export type WorkerJobStartMessage = {
57
- type: WorkerMessageType.running;
61
+ type: 'running';
58
62
  uid: number;
59
63
  resultType: 'observable' | 'promise';
60
64
  };
@@ -1,16 +1,15 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.WorkerMessageType = exports.MasterMessageType = void 0;
4
- var MasterMessageType;
5
- (function (MasterMessageType) {
6
- MasterMessageType["cancel"] = "cancel";
7
- MasterMessageType["run"] = "run";
8
- })(MasterMessageType || (exports.MasterMessageType = MasterMessageType = {}));
9
- var WorkerMessageType;
10
- (function (WorkerMessageType) {
11
- WorkerMessageType["error"] = "error";
12
- WorkerMessageType["init"] = "init";
13
- WorkerMessageType["result"] = "result";
14
- WorkerMessageType["running"] = "running";
15
- WorkerMessageType["uncaughtError"] = "uncaughtError";
16
- })(WorkerMessageType || (exports.WorkerMessageType = WorkerMessageType = {}));
4
+ const enum_1 = require("../enum");
5
+ exports.MasterMessageType = (0, enum_1.Enum)({
6
+ cancel: 'cancel',
7
+ run: 'run',
8
+ });
9
+ exports.WorkerMessageType = (0, enum_1.Enum)({
10
+ error: 'error',
11
+ init: 'init',
12
+ result: 'result',
13
+ running: 'running',
14
+ uncaughtError: 'uncaughtError',
15
+ });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@xylabs/threads",
3
- "version": "4.4.35",
3
+ "version": "4.5.0",
4
4
  "description": "Web workers & worker threads as simple as a function call",
5
5
  "license": "MIT",
6
6
  "main": "dist/index.js",
@@ -91,22 +91,21 @@
91
91
  "observable-fns": "^0.6.1"
92
92
  },
93
93
  "devDependencies": {
94
- "@babel/types": "^7.26.3",
94
+ "@babel/types": "^7.26.5",
95
95
  "@rollup/plugin-commonjs": "^28.0.2",
96
96
  "@rollup/plugin-node-resolve": "^16.0.0",
97
97
  "@types/debug": "^4.1.12",
98
- "@types/node": "^22.10.4",
98
+ "@types/node": "^22.10.7",
99
99
  "@xylabs/ts-scripts-yarn3": "^4.2.6",
100
100
  "cross-env": "^7.0.3",
101
101
  "puppet-run": "^0.11.4",
102
102
  "raw-loader": "^4.0.2",
103
103
  "rimraf": "^6.0.1",
104
- "rollup": "^4.29.1",
104
+ "rollup": "^4.31.0",
105
105
  "threads-plugin": "^1.4.0",
106
106
  "tiny-worker": "^2.3.0",
107
- "tslib": "^2.8.1",
108
- "typescript": "^5.7.2",
109
- "vitest": "^2.1.8",
107
+ "typescript": "^5.7.3",
108
+ "vitest": "^3.0.3",
110
109
  "webpack": "^5.97.1"
111
110
  },
112
111
  "optionalDependencies": {
package/src/enum.ts ADDED
@@ -0,0 +1,87 @@
1
+ /**
2
+ * Transforms a given record object into a readonly "enum-like" structure while preserving
3
+ * the literal types of its values. This allows you to use the returned object both at runtime
4
+ * (for lookups) and at compile time (for strongly typed values).
5
+ *
6
+ * To maintain literal types (i.e., prevent them from being widened to `string`, `number`, etc.),
7
+ * ensure you annotate your object with `as const` before passing it to `Enum`.
8
+ *
9
+ * @template T - A record type with string keys and any kind of values.
10
+ * @param obj - A readonly record object annotated with `as const`.
11
+ * @returns A readonly version of the provided record, preserving exact literal value types.
12
+ *
13
+ * @example
14
+ * ```typescript
15
+ * // Defining a record with literal types using as const:
16
+ * const DnsRecordType = Enum({
17
+ * A: 1,
18
+ * AAAA: 28,
19
+ * CAA: 257,
20
+ * CNAME: 5,
21
+ * DNAME: 39,
22
+ * MX: 15,
23
+ * NS: 2,
24
+ * PTR: 12,
25
+ * SOA: 6,
26
+ * SPF: 99,
27
+ * SRV: 33,
28
+ * TXT: 16,
29
+ * } as const);
30
+ *
31
+ * // DnsRecordType is now a readonly object:
32
+ * // {
33
+ * // readonly A: 1;
34
+ * // readonly AAAA: 28;
35
+ * // readonly CAA: 257;
36
+ * // readonly CNAME: 5;
37
+ * // readonly DNAME: 39;
38
+ * // readonly MX: 15;
39
+ * // readonly NS: 2;
40
+ * // readonly PTR: 12;
41
+ * // readonly SOA: 6;
42
+ * // readonly SPF: 99;
43
+ * // readonly SRV: 33;
44
+ * // readonly TXT: 16;
45
+ * // }
46
+ * ```
47
+ */
48
+ export const Enum = <const T extends Record<string | number | symbol, unknown>>(obj: Readonly<T>): Enum<T> => {
49
+ return obj
50
+ }
51
+
52
+ /**
53
+ * A utility type that, given a `Record<string, unknown>`, returns a readonly version
54
+ * of that record. This results in a type where all properties of `T` are readonly.
55
+ *
56
+ * @template T - The record type to make readonly.
57
+ *
58
+ * @example
59
+ * ```typescript
60
+ * // Given a record:
61
+ * export const DnsRecordType = Enum({
62
+ * A: 1,
63
+ * AAAA: 28,
64
+ * CAA: 257,
65
+ * CNAME: 5,
66
+ * DNAME: 39,
67
+ * MX: 15,
68
+ * NS: 2,
69
+ * PTR: 12,
70
+ * SOA: 6,
71
+ * SPF: 99,
72
+ * SRV: 33,
73
+ * TXT: 16,
74
+ * })
75
+ *
76
+ * // Now the type inference will preserve the literal types:
77
+ * export type DnsRecordType = Enum<typeof DnsRecordType>
78
+ * ```
79
+ */
80
+ export type Enum<T extends Readonly<Record<string | number | symbol, unknown>>> = {
81
+ readonly [K in keyof T]: T[K]
82
+ }
83
+
84
+ /**
85
+ * A utility type that, given an `Enum` object, returns the union of its values.
86
+ */
87
+ export type EnumValue<T extends Record<string | number | symbol, unknown>, K = Enum<T>> = K[keyof K]
@@ -1,57 +1,61 @@
1
1
  /* eslint-disable @typescript-eslint/no-explicit-any */
2
2
  /* eslint-disable @typescript-eslint/member-ordering */
3
+ import type { EnumValue } from '../enum'
4
+ import { Enum } from '../enum'
3
5
  import type { Thread } from './thread'
4
6
 
5
7
  /** Pool event type. Specifies the type of each `PoolEvent`. */
6
- export enum PoolEventType {
7
- initialized = 'initialized',
8
- taskCanceled = 'taskCanceled',
9
- taskCompleted = 'taskCompleted',
10
- taskFailed = 'taskFailed',
11
- taskQueued = 'taskQueued',
12
- taskQueueDrained = 'taskQueueDrained',
13
- taskStart = 'taskStart',
14
- terminated = 'terminated',
15
- }
8
+ export const PoolEventType = Enum({
9
+ initialized: 'initialized',
10
+ taskCanceled: 'taskCanceled',
11
+ taskCompleted: 'taskCompleted',
12
+ taskFailed: 'taskFailed',
13
+ taskQueued: 'taskQueued',
14
+ taskQueueDrained: 'taskQueueDrained',
15
+ taskStart: 'taskStart',
16
+ terminated: 'terminated',
17
+ })
18
+
19
+ export type PoolEventType = EnumValue<typeof PoolEventType>
16
20
 
17
21
  export type TaskRunFunction<ThreadType extends Thread, Return> = (worker: ThreadType) => Promise<Return>
18
22
 
19
23
  /** Pool event. Subscribe to those events using `pool.events()`. Useful for debugging. */
20
24
  export type PoolEvent<ThreadType extends Thread> =
21
25
  | {
22
- type: PoolEventType.initialized
26
+ type: 'initialized'
23
27
  size: number
24
28
  }
25
29
  | {
26
- type: PoolEventType.taskQueued
30
+ type: 'taskQueued'
27
31
  taskID: number
28
32
  }
29
33
  | {
30
- type: PoolEventType.taskQueueDrained
34
+ type: 'taskQueueDrained'
31
35
  }
32
36
  | {
33
- type: PoolEventType.taskStart
37
+ type: 'taskStart'
34
38
  taskID: number
35
39
  workerID: number
36
40
  }
37
41
  | {
38
- type: PoolEventType.taskCompleted
42
+ type: 'taskCompleted'
39
43
  returnValue: any
40
44
  taskID: number
41
45
  workerID: number
42
46
  }
43
47
  | {
44
- type: PoolEventType.taskFailed
48
+ type: 'taskFailed'
45
49
  error: Error
46
50
  taskID: number
47
51
  workerID: number
48
52
  }
49
53
  | {
50
- type: PoolEventType.taskCanceled
54
+ type: 'taskCanceled'
51
55
  taskID: number
52
56
  }
53
57
  | {
54
- type: PoolEventType.terminated
58
+ type: 'terminated'
55
59
  remainingQueue: Array<QueuedTask<ThreadType, any>>
56
60
  }
57
61
 
@@ -6,13 +6,12 @@
6
6
  /* eslint-disable unicorn/no-array-reduce */
7
7
  /* eslint-disable @typescript-eslint/no-explicit-any */
8
8
  /* eslint-disable @typescript-eslint/no-namespace */
9
- /* eslint-disable @typescript-eslint/no-floating-promises */
9
+
10
10
  import DebugLogger from 'debug'
11
11
  import {
12
12
  multicast, Observable, Subject,
13
13
  } from 'observable-fns'
14
14
 
15
- import { allSettled } from '../ponyfills'
16
15
  import { defaultPoolSize } from './implementation'
17
16
  import type {
18
17
  PoolEvent, QueuedTask, TaskRunFunction, WorkerDescriptor,
@@ -224,7 +223,10 @@ class WorkerPool<ThreadType extends Thread> implements Pool<ThreadType> {
224
223
  return
225
224
  }
226
225
 
227
- this.run(availableWorker, nextTask)
226
+ this.run(availableWorker, nextTask).catch((error) => {
227
+ this.debug('Error while running task:', error)
228
+ this.eventSubject.error(error)
229
+ })
228
230
  }
229
231
 
230
232
  private taskCompletion(taskID: number) {
@@ -259,7 +261,7 @@ class WorkerPool<ThreadType extends Thread> implements Pool<ThreadType> {
259
261
  throw this.initErrors[0]
260
262
  }
261
263
  if (allowResolvingImmediately && this.taskQueue.length === 0) {
262
- await allSettled(getCurrentlyRunningTasks())
264
+ await Promise.allSettled(getCurrentlyRunningTasks())
263
265
  return taskFailures
264
266
  }
265
267
 
@@ -275,7 +277,7 @@ class WorkerPool<ThreadType extends Thread> implements Pool<ThreadType> {
275
277
  })
276
278
  })
277
279
 
278
- await allSettled(getCurrentlyRunningTasks())
280
+ await Promise.allSettled(getCurrentlyRunningTasks())
279
281
  failureSubscription.unsubscribe()
280
282
 
281
283
  return taskFailures
@@ -6,6 +6,8 @@
6
6
  // See <https://github.com/microsoft/TypeScript/issues/28009>
7
7
  import type { Observable } from 'observable-fns'
8
8
 
9
+ import type { EnumValue } from '../enum'
10
+ import { Enum } from '../enum'
9
11
  import type { ObservablePromise } from '../observable-promise'
10
12
  import type {
11
13
  $errors, $events, $terminate, $worker,
@@ -64,11 +66,9 @@ interface AnyModuleThread extends PrivateThreadProps {
64
66
  /** Worker thread. Either a `FunctionThread` or a `ModuleThread`. */
65
67
  export type Thread = AnyFunctionThread | AnyModuleThread
66
68
 
67
- export type TransferList = Transferable[]
68
-
69
69
  /** Worker instance. Either a web worker or a node.js Worker provided by `worker_threads` or `tiny-worker`. */
70
70
  export interface Worker extends EventTarget {
71
- postMessage(value: any, transferList?: TransferList): void
71
+ postMessage(value: any, transferList?: Transferable[]): void
72
72
  /** In nodejs 10+ return type is Promise while with tiny-worker and in browser return type is void */
73
73
  terminate(callback?: (error?: Error, exitCode?: number) => void): void | Promise<number>
74
74
  }
@@ -93,7 +93,7 @@ export interface ThreadsWorkerOptions extends WorkerOptions {
93
93
  /** Worker implementation. Either web worker or a node.js Worker class. */
94
94
  export declare class WorkerImplementation extends EventTarget implements Worker {
95
95
  constructor(path: string, options?: ThreadsWorkerOptions)
96
- postMessage(value: any, transferList?: TransferList): void
96
+ postMessage(value: any, transferList?: Transferable[]): void
97
97
  terminate(): void | Promise<number>
98
98
  }
99
99
 
@@ -109,24 +109,26 @@ export interface ImplementationExport {
109
109
  }
110
110
 
111
111
  /** Event as emitted by worker thread. Subscribe to using `Thread.events(thread)`. */
112
- export enum WorkerEventType {
113
- internalError = 'internalError',
114
- message = 'message',
115
- termination = 'termination',
116
- }
112
+ export const WorkerEventType = Enum({
113
+ internalError: 'internalError',
114
+ message: 'message',
115
+ termination: 'termination',
116
+ })
117
+
118
+ export type WorkerEventType = EnumValue<typeof WorkerEventType>
117
119
 
118
120
  export interface WorkerInternalErrorEvent {
119
121
  error: Error
120
- type: WorkerEventType.internalError
122
+ type: 'internalError'
121
123
  }
122
124
 
123
125
  export interface WorkerMessageEvent<Data> {
124
126
  data: Data
125
- type: WorkerEventType.message
127
+ type: 'message'
126
128
  }
127
129
 
128
130
  export interface WorkerTerminationEvent {
129
- type: WorkerEventType.termination
131
+ type: 'termination'
130
132
  }
131
133
 
132
134
  export type WorkerEvent = WorkerInternalErrorEvent | WorkerMessageEvent<any> | WorkerTerminationEvent
@@ -1,4 +1,8 @@
1
1
  /* eslint-disable @typescript-eslint/no-explicit-any */
2
+
3
+ import type { EnumValue } from '../enum'
4
+ import { Enum } from '../enum'
5
+
2
6
  /* eslint-disable @typescript-eslint/member-ordering */
3
7
  export interface SerializedError {
4
8
  __error_marker: '$$error'
@@ -10,18 +14,20 @@ export interface SerializedError {
10
14
  /////////////////////////////
11
15
  // Messages sent by master:
12
16
 
13
- export enum MasterMessageType {
14
- cancel = 'cancel',
15
- run = 'run',
16
- }
17
+ export const MasterMessageType = Enum({
18
+ cancel: 'cancel',
19
+ run: 'run',
20
+ })
21
+
22
+ export type MasterMessageType = EnumValue<typeof MasterMessageType>
17
23
 
18
24
  export type MasterJobCancelMessage = {
19
- type: MasterMessageType.cancel
25
+ type: 'cancel'
20
26
  uid: number
21
27
  }
22
28
 
23
29
  export type MasterJobRunMessage = {
24
- type: MasterMessageType.run
30
+ type: 'run'
25
31
  uid: number
26
32
  method?: string
27
33
  args: any[]
@@ -30,16 +36,18 @@ export type MasterJobRunMessage = {
30
36
  ////////////////////////////
31
37
  // Messages sent by worker:
32
38
 
33
- export enum WorkerMessageType {
34
- error = 'error',
35
- init = 'init',
36
- result = 'result',
37
- running = 'running',
38
- uncaughtError = 'uncaughtError',
39
- }
39
+ export const WorkerMessageType = Enum({
40
+ error: 'error',
41
+ init: 'init',
42
+ result: 'result',
43
+ running: 'running',
44
+ uncaughtError: 'uncaughtError',
45
+ })
46
+
47
+ export type WorkerMessageType = EnumValue<typeof WorkerMessageType>
40
48
 
41
49
  export type WorkerUncaughtErrorMessage = {
42
- type: WorkerMessageType.uncaughtError
50
+ type: 'uncaughtError'
43
51
  error: {
44
52
  message: string
45
53
  name: string
@@ -48,25 +56,25 @@ export type WorkerUncaughtErrorMessage = {
48
56
  }
49
57
 
50
58
  export type WorkerInitMessage = {
51
- type: WorkerMessageType.init
59
+ type: 'init'
52
60
  exposed: { type: 'function' } | { type: 'module'; methods: string[] }
53
61
  }
54
62
 
55
63
  export type WorkerJobErrorMessage = {
56
- type: WorkerMessageType.error
64
+ type: 'error'
57
65
  uid: number
58
66
  error: SerializedError
59
67
  }
60
68
 
61
69
  export type WorkerJobResultMessage = {
62
- type: WorkerMessageType.result
70
+ type: 'result'
63
71
  uid: number
64
72
  complete?: true
65
73
  payload?: any
66
74
  }
67
75
 
68
76
  export type WorkerJobStartMessage = {
69
- type: WorkerMessageType.running
77
+ type: 'running'
70
78
  uid: number
71
79
  resultType: 'observable' | 'promise'
72
80
  }
@@ -1,20 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.allSettled = allSettled;
4
- function allSettled(values) {
5
- return Promise.all(values.map((item) => {
6
- const onFulfill = (value) => {
7
- return { status: 'fulfilled', value };
8
- };
9
- const onReject = (reason) => {
10
- return { reason, status: 'rejected' };
11
- };
12
- const itemPromise = Promise.resolve(item);
13
- try {
14
- return itemPromise.then(onFulfill, onReject);
15
- }
16
- catch (error) {
17
- return Promise.reject(error);
18
- }
19
- }));
20
- }
@@ -1,8 +0,0 @@
1
- export type SettlementResult<T> = {
2
- status: 'fulfilled';
3
- value: T;
4
- } | {
5
- reason: any;
6
- status: 'rejected';
7
- };
8
- export declare function allSettled<T>(values: T[]): Promise<Array<SettlementResult<T>>>;
package/dist/ponyfills.js DELETED
@@ -1,20 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.allSettled = allSettled;
4
- function allSettled(values) {
5
- return Promise.all(values.map((item) => {
6
- const onFulfill = (value) => {
7
- return { status: 'fulfilled', value };
8
- };
9
- const onReject = (reason) => {
10
- return { reason, status: 'rejected' };
11
- };
12
- const itemPromise = Promise.resolve(item);
13
- try {
14
- return itemPromise.then(onFulfill, onReject);
15
- }
16
- catch (error) {
17
- return Promise.reject(error);
18
- }
19
- }));
20
- }
package/src/ponyfills.ts DELETED
@@ -1,31 +0,0 @@
1
- /* eslint-disable @typescript-eslint/no-explicit-any */
2
- export type SettlementResult<T> =
3
- | {
4
- status: 'fulfilled'
5
- value: T
6
- }
7
- | {
8
- reason: any
9
- status: 'rejected'
10
- }
11
-
12
- // Based on <https://github.com/es-shims/Promise.allSettled/blob/master/implementation.js>
13
- export function allSettled<T>(values: T[]): Promise<Array<SettlementResult<T>>> {
14
- return Promise.all(
15
- values.map((item) => {
16
- const onFulfill = (value: T) => {
17
- return { status: 'fulfilled', value } as const
18
- }
19
- const onReject = (reason: any) => {
20
- return { reason, status: 'rejected' } as const
21
- }
22
-
23
- const itemPromise = Promise.resolve(item)
24
- try {
25
- return itemPromise.then(onFulfill, onReject)
26
- } catch (error) {
27
- return Promise.reject(error)
28
- }
29
- }),
30
- )
31
- }