@bluelibs/runner 4.8.6 → 4.9.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/AI.md +8 -0
- package/README.md +39 -4
- package/dist/browser/index.cjs +543 -418
- package/dist/browser/index.cjs.map +1 -1
- package/dist/browser/index.d.mts +2221 -0
- package/dist/browser/index.d.ts +2221 -0
- package/dist/browser/index.mjs +543 -418
- package/dist/browser/index.mjs.map +1 -1
- package/dist/edge/index.cjs +543 -418
- package/dist/edge/index.cjs.map +1 -1
- package/dist/edge/index.d.mts +2221 -0
- package/dist/edge/index.d.ts +2221 -0
- package/dist/edge/index.mjs +543 -418
- package/dist/edge/index.mjs.map +1 -1
- package/dist/node/node.cjs +584 -436
- package/dist/node/node.cjs.map +1 -1
- package/dist/node/node.d.mts +2472 -0
- package/dist/node/node.d.ts +2425 -55
- package/dist/node/node.mjs +584 -436
- package/dist/node/node.mjs.map +1 -1
- package/dist/universal/index.cjs +541 -418
- package/dist/universal/index.cjs.map +1 -1
- package/dist/universal/index.d.mts +2221 -0
- package/dist/universal/index.d.ts +2221 -0
- package/dist/universal/index.mjs +541 -418
- package/dist/universal/index.mjs.map +1 -1
- package/package.json +5 -5
- package/dist/define.d.ts +0 -9
- package/dist/definers/builders/asyncContext.d.ts +0 -13
- package/dist/definers/builders/core.d.ts +0 -30
- package/dist/definers/builders/error.d.ts +0 -15
- package/dist/definers/builders/event.d.ts +0 -12
- package/dist/definers/builders/hook.d.ts +0 -20
- package/dist/definers/builders/middleware.d.ts +0 -39
- package/dist/definers/builders/resource.d.ts +0 -40
- package/dist/definers/builders/tag.d.ts +0 -10
- package/dist/definers/builders/task.d.ts +0 -37
- package/dist/definers/builders/task.phantom.d.ts +0 -27
- package/dist/definers/builders/utils.d.ts +0 -4
- package/dist/definers/defineAsyncContext.d.ts +0 -15
- package/dist/definers/defineError.d.ts +0 -26
- package/dist/definers/defineEvent.d.ts +0 -2
- package/dist/definers/defineHook.d.ts +0 -6
- package/dist/definers/defineOverride.d.ts +0 -17
- package/dist/definers/defineResource.d.ts +0 -2
- package/dist/definers/defineResourceMiddleware.d.ts +0 -2
- package/dist/definers/defineTag.d.ts +0 -12
- package/dist/definers/defineTask.d.ts +0 -18
- package/dist/definers/defineTaskMiddleware.d.ts +0 -2
- package/dist/definers/tools.d.ts +0 -53
- package/dist/defs.d.ts +0 -31
- package/dist/errors.d.ts +0 -62
- package/dist/globals/debug.d.ts +0 -10
- package/dist/globals/globalEvents.d.ts +0 -8
- package/dist/globals/globalMiddleware.d.ts +0 -31
- package/dist/globals/globalResources.d.ts +0 -41
- package/dist/globals/globalTags.d.ts +0 -11
- package/dist/globals/middleware/cache.middleware.d.ts +0 -27
- package/dist/globals/middleware/requireContext.middleware.d.ts +0 -6
- package/dist/globals/middleware/retry.middleware.d.ts +0 -21
- package/dist/globals/middleware/timeout.middleware.d.ts +0 -9
- package/dist/globals/middleware/tunnel.middleware.d.ts +0 -2
- package/dist/globals/resources/debug/debug.resource.d.ts +0 -7
- package/dist/globals/resources/debug/debug.tag.d.ts +0 -2
- package/dist/globals/resources/debug/debugConfig.resource.d.ts +0 -22
- package/dist/globals/resources/debug/executionTracker.middleware.d.ts +0 -50
- package/dist/globals/resources/debug/globalEvent.hook.d.ts +0 -27
- package/dist/globals/resources/debug/hook.hook.d.ts +0 -30
- package/dist/globals/resources/debug/index.d.ts +0 -6
- package/dist/globals/resources/debug/middleware.hook.d.ts +0 -30
- package/dist/globals/resources/debug/types.d.ts +0 -25
- package/dist/globals/resources/debug/utils.d.ts +0 -2
- package/dist/globals/resources/httpClientFactory.resource.d.ts +0 -28
- package/dist/globals/resources/queue.resource.d.ts +0 -10
- package/dist/globals/resources/tunnel/ejson-extensions.d.ts +0 -1
- package/dist/globals/resources/tunnel/error-utils.d.ts +0 -1
- package/dist/globals/resources/tunnel/plan.d.ts +0 -19
- package/dist/globals/resources/tunnel/protocol.d.ts +0 -47
- package/dist/globals/resources/tunnel/serializer.d.ts +0 -9
- package/dist/globals/resources/tunnel/tunnel.policy.tag.d.ts +0 -18
- package/dist/globals/resources/tunnel/tunnel.tag.d.ts +0 -2
- package/dist/globals/resources/tunnel/types.d.ts +0 -42
- package/dist/globals/tunnels/index.d.ts +0 -23
- package/dist/globals/types.d.ts +0 -4
- package/dist/http-client.d.ts +0 -25
- package/dist/http-fetch-tunnel.resource.d.ts +0 -11
- package/dist/index.d.ts +0 -117
- package/dist/models/DependencyProcessor.d.ts +0 -48
- package/dist/models/EventManager.d.ts +0 -153
- package/dist/models/LogPrinter.d.ts +0 -55
- package/dist/models/Logger.d.ts +0 -85
- package/dist/models/MiddlewareManager.d.ts +0 -75
- package/dist/models/OverrideManager.d.ts +0 -13
- package/dist/models/Queue.d.ts +0 -26
- package/dist/models/ResourceInitializer.d.ts +0 -20
- package/dist/models/RunResult.d.ts +0 -35
- package/dist/models/Semaphore.d.ts +0 -61
- package/dist/models/Store.d.ts +0 -73
- package/dist/models/StoreRegistry.d.ts +0 -49
- package/dist/models/StoreValidator.d.ts +0 -8
- package/dist/models/TaskRunner.d.ts +0 -27
- package/dist/models/UnhandledError.d.ts +0 -11
- package/dist/models/index.d.ts +0 -11
- package/dist/models/middleware/InterceptorRegistry.d.ts +0 -56
- package/dist/models/middleware/MiddlewareResolver.d.ts +0 -31
- package/dist/models/middleware/ResourceMiddlewareComposer.d.ts +0 -34
- package/dist/models/middleware/TaskMiddlewareComposer.d.ts +0 -43
- package/dist/models/middleware/ValidationHelper.d.ts +0 -20
- package/dist/models/middleware/index.d.ts +0 -6
- package/dist/models/middleware/types.d.ts +0 -10
- package/dist/models/utils/findCircularDependencies.d.ts +0 -16
- package/dist/models/utils/safeStringify.d.ts +0 -3
- package/dist/node/exposure/allowList.d.ts +0 -3
- package/dist/node/exposure/authenticator.d.ts +0 -6
- package/dist/node/exposure/cors.d.ts +0 -4
- package/dist/node/exposure/createNodeExposure.d.ts +0 -2
- package/dist/node/exposure/exposureServer.d.ts +0 -18
- package/dist/node/exposure/httpResponse.d.ts +0 -10
- package/dist/node/exposure/logging.d.ts +0 -4
- package/dist/node/exposure/multipart.d.ts +0 -27
- package/dist/node/exposure/requestBody.d.ts +0 -11
- package/dist/node/exposure/requestContext.d.ts +0 -17
- package/dist/node/exposure/requestHandlers.d.ts +0 -24
- package/dist/node/exposure/resourceTypes.d.ts +0 -60
- package/dist/node/exposure/router.d.ts +0 -17
- package/dist/node/exposure/serverLifecycle.d.ts +0 -13
- package/dist/node/exposure/types.d.ts +0 -31
- package/dist/node/exposure/utils.d.ts +0 -17
- package/dist/node/exposure.resource.d.ts +0 -12
- package/dist/node/files.d.ts +0 -9
- package/dist/node/http-mixed-client.d.ts +0 -30
- package/dist/node/http-smart-client.model.d.ts +0 -24
- package/dist/node/index.d.ts +0 -1
- package/dist/node/inputFile.model.d.ts +0 -22
- package/dist/node/inputFile.utils.d.ts +0 -14
- package/dist/node/platform/createFile.d.ts +0 -9
- package/dist/node/resources/http-mixed-client.factory.resource.d.ts +0 -17
- package/dist/node/resources/http-smart-client.factory.resource.d.ts +0 -16
- package/dist/node/tunnel.allowlist.d.ts +0 -7
- package/dist/node/upload/manifest.d.ts +0 -22
- package/dist/platform/adapters/browser.d.ts +0 -14
- package/dist/platform/adapters/edge.d.ts +0 -5
- package/dist/platform/adapters/node-als.d.ts +0 -1
- package/dist/platform/adapters/node.d.ts +0 -15
- package/dist/platform/adapters/universal-generic.d.ts +0 -14
- package/dist/platform/adapters/universal.d.ts +0 -17
- package/dist/platform/createFile.d.ts +0 -10
- package/dist/platform/createWebFile.d.ts +0 -11
- package/dist/platform/factory.d.ts +0 -2
- package/dist/platform/index.d.ts +0 -27
- package/dist/platform/types.d.ts +0 -29
- package/dist/processHooks.d.ts +0 -2
- package/dist/run.d.ts +0 -14
- package/dist/testing.d.ts +0 -25
- package/dist/tools/getCallerFile.d.ts +0 -1
- package/dist/tunnels/buildUniversalManifest.d.ts +0 -24
- package/dist/types/asyncContext.d.ts +0 -41
- package/dist/types/contracts.d.ts +0 -63
- package/dist/types/error.d.ts +0 -36
- package/dist/types/event.d.ts +0 -74
- package/dist/types/hook.d.ts +0 -23
- package/dist/types/inputFile.d.ts +0 -34
- package/dist/types/meta.d.ts +0 -22
- package/dist/types/resource.d.ts +0 -87
- package/dist/types/resourceMiddleware.d.ts +0 -47
- package/dist/types/runner.d.ts +0 -68
- package/dist/types/storeTypes.d.ts +0 -40
- package/dist/types/symbols.d.ts +0 -32
- package/dist/types/tag.d.ts +0 -46
- package/dist/types/task.d.ts +0 -54
- package/dist/types/taskMiddleware.d.ts +0 -48
- package/dist/types/utilities.d.ts +0 -113
- package/dist/utils/detectRunnerMode.d.ts +0 -9
package/dist/edge/index.cjs
CHANGED
|
@@ -172,78 +172,87 @@ var cacheMiddleware = defineTaskMiddleware({
|
|
|
172
172
|
}
|
|
173
173
|
});
|
|
174
174
|
|
|
175
|
-
// src/
|
|
176
|
-
function
|
|
177
|
-
const
|
|
178
|
-
|
|
179
|
-
const err = new Error();
|
|
180
|
-
let callerfile;
|
|
181
|
-
let currentfile;
|
|
182
|
-
Error.prepareStackTrace = (err2, stack2) => stack2;
|
|
183
|
-
const stack = err.stack;
|
|
184
|
-
stack.shift();
|
|
185
|
-
currentfile = stack.shift()?.getFileName?.();
|
|
186
|
-
callerfile = stack.shift()?.getFileName?.();
|
|
187
|
-
return callerfile;
|
|
188
|
-
} finally {
|
|
189
|
-
Error.prepareStackTrace = originalFunc;
|
|
190
|
-
}
|
|
175
|
+
// src/platform/adapters/node-als.ts
|
|
176
|
+
async function loadAsyncLocalStorageClass() {
|
|
177
|
+
const mod = __require("async_hooks");
|
|
178
|
+
return mod.AsyncLocalStorage;
|
|
191
179
|
}
|
|
192
|
-
__name(
|
|
180
|
+
__name(loadAsyncLocalStorageClass, "loadAsyncLocalStorageClass");
|
|
193
181
|
|
|
194
|
-
// src/
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
182
|
+
// src/platform/adapters/node.ts
|
|
183
|
+
var NodePlatformAdapter = class {
|
|
184
|
+
constructor() {
|
|
185
|
+
this.id = "node";
|
|
186
|
+
this.setTimeout = globalThis.setTimeout;
|
|
187
|
+
this.clearTimeout = globalThis.clearTimeout;
|
|
188
|
+
}
|
|
189
|
+
static {
|
|
190
|
+
__name(this, "NodePlatformAdapter");
|
|
191
|
+
}
|
|
192
|
+
async init() {
|
|
193
|
+
this.alsClass = await loadAsyncLocalStorageClass();
|
|
194
|
+
}
|
|
195
|
+
onUncaughtException(handler) {
|
|
196
|
+
process.on("uncaughtException", handler);
|
|
197
|
+
return () => process.off("uncaughtException", handler);
|
|
198
|
+
}
|
|
199
|
+
onUnhandledRejection(handler) {
|
|
200
|
+
const h = /* @__PURE__ */ __name((reason) => handler(reason), "h");
|
|
201
|
+
process.on("unhandledRejection", h);
|
|
202
|
+
return () => process.off("unhandledRejection", h);
|
|
203
|
+
}
|
|
204
|
+
onShutdownSignal(handler) {
|
|
205
|
+
process.on("SIGINT", handler);
|
|
206
|
+
process.on("SIGTERM", handler);
|
|
207
|
+
return () => {
|
|
208
|
+
process.off("SIGINT", handler);
|
|
209
|
+
process.off("SIGTERM", handler);
|
|
210
|
+
};
|
|
211
|
+
}
|
|
212
|
+
exit(code) {
|
|
213
|
+
process.exit(code);
|
|
214
|
+
}
|
|
215
|
+
getEnv(key) {
|
|
216
|
+
return process.env[key];
|
|
217
|
+
}
|
|
218
|
+
hasAsyncLocalStorage() {
|
|
219
|
+
return true;
|
|
220
|
+
}
|
|
221
|
+
createAsyncLocalStorage() {
|
|
222
|
+
let instance;
|
|
223
|
+
const ensure = /* @__PURE__ */ __name(() => {
|
|
224
|
+
if (!this.alsClass) {
|
|
225
|
+
let als;
|
|
226
|
+
const forceNoop = typeof process !== "undefined" && !!process.env?.RUNNER_FORCE_NOOP_ALS;
|
|
227
|
+
if (!forceNoop) {
|
|
228
|
+
try {
|
|
229
|
+
const mod = __require("async_hooks");
|
|
230
|
+
als = mod?.AsyncLocalStorage;
|
|
231
|
+
} catch (_) {
|
|
232
|
+
als = void 0;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
this.alsClass = als ? als : class NoopAsyncLocalStorage {
|
|
236
|
+
static {
|
|
237
|
+
__name(this, "NoopAsyncLocalStorage");
|
|
238
|
+
}
|
|
239
|
+
getStore() {
|
|
240
|
+
return void 0;
|
|
241
|
+
}
|
|
242
|
+
run(_store, callback) {
|
|
243
|
+
return callback();
|
|
244
|
+
}
|
|
245
|
+
};
|
|
246
|
+
}
|
|
247
|
+
return instance ??= new this.alsClass();
|
|
248
|
+
}, "ensure");
|
|
249
|
+
return {
|
|
250
|
+
getStore: /* @__PURE__ */ __name(() => ensure().getStore(), "getStore"),
|
|
251
|
+
run: /* @__PURE__ */ __name((store2, callback) => ensure().run(store2, callback), "run")
|
|
252
|
+
};
|
|
253
|
+
}
|
|
228
254
|
};
|
|
229
255
|
|
|
230
|
-
// src/definers/defineHook.ts
|
|
231
|
-
function defineHook(hookDef) {
|
|
232
|
-
const filePath = getCallerFile();
|
|
233
|
-
return {
|
|
234
|
-
[symbolHook]: true,
|
|
235
|
-
[symbolFilePath]: filePath,
|
|
236
|
-
id: hookDef.id,
|
|
237
|
-
dependencies: hookDef.dependencies || {},
|
|
238
|
-
on: hookDef.on,
|
|
239
|
-
order: hookDef.order,
|
|
240
|
-
run: hookDef.run,
|
|
241
|
-
meta: hookDef.meta || {},
|
|
242
|
-
tags: hookDef.tags || []
|
|
243
|
-
};
|
|
244
|
-
}
|
|
245
|
-
__name(defineHook, "defineHook");
|
|
246
|
-
|
|
247
256
|
// src/errors.ts
|
|
248
257
|
var errors_exports = {};
|
|
249
258
|
__export(errors_exports, {
|
|
@@ -370,86 +379,93 @@ function errorBuilder(id2) {
|
|
|
370
379
|
__name(errorBuilder, "errorBuilder");
|
|
371
380
|
var error = errorBuilder;
|
|
372
381
|
|
|
373
|
-
// src/
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
process.on("unhandledRejection", h);
|
|
400
|
-
return () => process.off("unhandledRejection", h);
|
|
401
|
-
}
|
|
402
|
-
onShutdownSignal(handler) {
|
|
403
|
-
process.on("SIGINT", handler);
|
|
404
|
-
process.on("SIGTERM", handler);
|
|
405
|
-
return () => {
|
|
406
|
-
process.off("SIGINT", handler);
|
|
407
|
-
process.off("SIGTERM", handler);
|
|
408
|
-
};
|
|
409
|
-
}
|
|
410
|
-
exit(code) {
|
|
411
|
-
process.exit(code);
|
|
412
|
-
}
|
|
413
|
-
getEnv(key) {
|
|
414
|
-
return process.env[key];
|
|
415
|
-
}
|
|
416
|
-
hasAsyncLocalStorage() {
|
|
417
|
-
return true;
|
|
418
|
-
}
|
|
419
|
-
createAsyncLocalStorage() {
|
|
420
|
-
let instance;
|
|
421
|
-
const ensure = /* @__PURE__ */ __name(() => {
|
|
422
|
-
if (!this.alsClass) {
|
|
423
|
-
let als;
|
|
424
|
-
const forceNoop = typeof process !== "undefined" && !!process.env?.RUNNER_FORCE_NOOP_ALS;
|
|
425
|
-
if (!forceNoop) {
|
|
426
|
-
try {
|
|
427
|
-
const mod = __require("async_hooks");
|
|
428
|
-
als = mod?.AsyncLocalStorage;
|
|
429
|
-
} catch (_) {
|
|
430
|
-
als = void 0;
|
|
431
|
-
}
|
|
432
|
-
}
|
|
433
|
-
this.alsClass = als ? als : class NoopAsyncLocalStorage {
|
|
434
|
-
static {
|
|
435
|
-
__name(this, "NoopAsyncLocalStorage");
|
|
436
|
-
}
|
|
437
|
-
getStore() {
|
|
438
|
-
return void 0;
|
|
439
|
-
}
|
|
440
|
-
run(_store, callback) {
|
|
441
|
-
return callback();
|
|
442
|
-
}
|
|
443
|
-
};
|
|
444
|
-
}
|
|
445
|
-
return instance ??= new this.alsClass();
|
|
446
|
-
}, "ensure");
|
|
447
|
-
return {
|
|
448
|
-
getStore: /* @__PURE__ */ __name(() => ensure().getStore(), "getStore"),
|
|
449
|
-
run: /* @__PURE__ */ __name((store2, callback) => ensure().run(store2, callback), "run")
|
|
450
|
-
};
|
|
382
|
+
// src/errors.ts
|
|
383
|
+
var duplicateRegistrationError = error("runner.errors.duplicateRegistration").format(
|
|
384
|
+
({ type, id: id2 }) => `${type} "${id2.toString()}" already registered. You might have used the same 'id' in two different components or you may have registered the same element twice.`
|
|
385
|
+
).build();
|
|
386
|
+
var dependencyNotFoundError = error("runner.errors.dependencyNotFound").format(
|
|
387
|
+
({ key }) => `Dependency ${key.toString()} not found. Did you forget to register it through a resource?`
|
|
388
|
+
).build();
|
|
389
|
+
var unknownItemTypeError = error(
|
|
390
|
+
"runner.errors.unknownItemType"
|
|
391
|
+
).format(
|
|
392
|
+
({ item }) => `Unknown item type: ${String(
|
|
393
|
+
item
|
|
394
|
+
)}. Please ensure you are not using different versions of '@bluelibs/runner'`
|
|
395
|
+
).build();
|
|
396
|
+
var contextError = error(
|
|
397
|
+
"runner.errors.context"
|
|
398
|
+
).format(({ details }) => details ?? "Context error").build();
|
|
399
|
+
var circularDependenciesError = error("runner.errors.circularDependencies").format(({ cycles }) => {
|
|
400
|
+
const cycleDetails = cycles.map((cycle) => ` \u2022 ${cycle}`).join("\n");
|
|
401
|
+
const hasMiddleware = cycles.some((cycle) => cycle.includes("middleware"));
|
|
402
|
+
let guidance = "\n\nTo resolve circular dependencies:";
|
|
403
|
+
guidance += "\n \u2022 Consider refactoring to reduce coupling between components";
|
|
404
|
+
guidance += "\n \u2022 Extract shared dependencies into separate resources";
|
|
405
|
+
if (hasMiddleware) {
|
|
406
|
+
guidance += "\n \u2022 For middleware: you can filter out tasks/resources using everywhere(fn)";
|
|
407
|
+
guidance += "\n \u2022 Consider using events for communication instead of direct dependencies";
|
|
451
408
|
}
|
|
452
|
-
|
|
409
|
+
return `Circular dependencies detected:
|
|
410
|
+
${cycleDetails}${guidance}`;
|
|
411
|
+
}).build();
|
|
412
|
+
var eventNotFoundError = error(
|
|
413
|
+
"runner.errors.eventNotFound"
|
|
414
|
+
).format(
|
|
415
|
+
({ id: id2 }) => `Event "${id2.toString()}" not found. Did you forget to register it?`
|
|
416
|
+
).build();
|
|
417
|
+
var resourceNotFoundError = error(
|
|
418
|
+
"runner.errors.resourceNotFound"
|
|
419
|
+
).format(
|
|
420
|
+
({ id: id2 }) => `Resource "${id2.toString()}" not found. Did you forget to register it or are you using the correct id?`
|
|
421
|
+
).build();
|
|
422
|
+
var middlewareNotRegisteredError = error("runner.errors.middlewareNotRegistered").format(
|
|
423
|
+
({ type, source, middlewareId }) => `Middleware inside ${type} "${source}" depends on "${middlewareId}" but it's not registered. Did you forget to register it?`
|
|
424
|
+
).build();
|
|
425
|
+
var tagNotFoundError = error(
|
|
426
|
+
"runner.errors.tagNotFound"
|
|
427
|
+
).format(
|
|
428
|
+
({ id: id2 }) => `Tag "${id2}" not registered. Did you forget to register it inside a resource?`
|
|
429
|
+
).build();
|
|
430
|
+
var lockedError = error(
|
|
431
|
+
"runner.errors.locked"
|
|
432
|
+
).format(
|
|
433
|
+
({ what }) => `Cannot modify the ${what.toString()} when it is locked.`
|
|
434
|
+
).build();
|
|
435
|
+
var storeAlreadyInitializedError = error(
|
|
436
|
+
"runner.errors.storeAlreadyInitialized"
|
|
437
|
+
).format(() => "Store already initialized. Cannot reinitialize.").build();
|
|
438
|
+
var validationError = error("runner.errors.validation").format(({ subject, id: id2, originalError }) => {
|
|
439
|
+
const errorMessage = originalError instanceof Error ? originalError.message : String(originalError);
|
|
440
|
+
return `${subject} validation failed for ${id2.toString()}: ${errorMessage}`;
|
|
441
|
+
}).build();
|
|
442
|
+
var eventCycleError = error("runner.errors.eventCycle").format(({ path }) => {
|
|
443
|
+
const chain = path.map((p) => `${p.id}\u2190${p.source}`).join(" -> ");
|
|
444
|
+
return `Event emission cycle detected:
|
|
445
|
+
${chain}
|
|
446
|
+
|
|
447
|
+
Break the cycle by changing hook logic (avoid mutual emits) or gate with conditions/tags.`;
|
|
448
|
+
}).build();
|
|
449
|
+
var eventEmissionCycleError = error("runner.errors.eventEmissionCycle").format(({ cycles }) => {
|
|
450
|
+
const list = cycles.map((c) => ` \u2022 ${c}`).join("\n");
|
|
451
|
+
return `Event emission cycles detected between hooks and events:
|
|
452
|
+
${list}
|
|
453
|
+
|
|
454
|
+
This was detected at compile time (dry-run). Break the cycle by avoiding mutual emits between hooks or scoping hooks using tags.`;
|
|
455
|
+
}).build();
|
|
456
|
+
var platformUnsupportedFunctionError = error("runner.errors.platformUnsupportedFunction").format(
|
|
457
|
+
({ functionName }) => `Platform function not supported in this environment: ${functionName}. Detected platform: ${detectEnvironment()}.`
|
|
458
|
+
).build();
|
|
459
|
+
var cancellationError = error(
|
|
460
|
+
"runner.errors.cancellation"
|
|
461
|
+
).format(({ reason }) => reason || "Operation cancelled").build();
|
|
462
|
+
var tunnelOwnershipConflictError = error("runner.errors.tunnelOwnershipConflict").format(
|
|
463
|
+
({ taskId, currentOwnerId, attemptedOwnerId }) => `Task "${taskId}" is already tunneled by resource "${currentOwnerId}". Resource "${attemptedOwnerId}" cannot tunnel it again. Ensure each task is owned by a single tunnel client.`
|
|
464
|
+
).build();
|
|
465
|
+
function isCancellationError(err) {
|
|
466
|
+
return cancellationError.is(err);
|
|
467
|
+
}
|
|
468
|
+
__name(isCancellationError, "isCancellationError");
|
|
453
469
|
|
|
454
470
|
// src/platform/adapters/browser.ts
|
|
455
471
|
var BrowserPlatformAdapter = class {
|
|
@@ -758,6 +774,12 @@ function setPlatform(adapter) {
|
|
|
758
774
|
adapter.id;
|
|
759
775
|
}
|
|
760
776
|
__name(setPlatform, "setPlatform");
|
|
777
|
+
function isNode() {
|
|
778
|
+
{
|
|
779
|
+
return false;
|
|
780
|
+
}
|
|
781
|
+
}
|
|
782
|
+
__name(isNode, "isNode");
|
|
761
783
|
var PlatformAdapter = class {
|
|
762
784
|
constructor(env) {
|
|
763
785
|
this.setTimeout = globalThis.setTimeout;
|
|
@@ -811,93 +833,79 @@ var PlatformAdapter = class {
|
|
|
811
833
|
}
|
|
812
834
|
};
|
|
813
835
|
|
|
814
|
-
// src/
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
var circularDependenciesError = error("runner.errors.circularDependencies").format(({ cycles }) => {
|
|
832
|
-
const cycleDetails = cycles.map((cycle) => ` \u2022 ${cycle}`).join("\n");
|
|
833
|
-
const hasMiddleware = cycles.some((cycle) => cycle.includes("middleware"));
|
|
834
|
-
let guidance = "\n\nTo resolve circular dependencies:";
|
|
835
|
-
guidance += "\n \u2022 Consider refactoring to reduce coupling between components";
|
|
836
|
-
guidance += "\n \u2022 Extract shared dependencies into separate resources";
|
|
837
|
-
if (hasMiddleware) {
|
|
838
|
-
guidance += "\n \u2022 For middleware: you can filter out tasks/resources using everywhere(fn)";
|
|
839
|
-
guidance += "\n \u2022 Consider using events for communication instead of direct dependencies";
|
|
836
|
+
// src/tools/getCallerFile.ts
|
|
837
|
+
function getCallerFile() {
|
|
838
|
+
const originalPrepare = Error.prepareStackTrace;
|
|
839
|
+
try {
|
|
840
|
+
if (isNode()) {
|
|
841
|
+
const err = new Error();
|
|
842
|
+
Error.prepareStackTrace = (_err, stack2) => stack2;
|
|
843
|
+
const stack = err.stack;
|
|
844
|
+
stack.shift();
|
|
845
|
+
stack.shift();
|
|
846
|
+
const candidate = stack.shift();
|
|
847
|
+
const file = candidate?.getFileName?.();
|
|
848
|
+
return file;
|
|
849
|
+
}
|
|
850
|
+
return "unknown";
|
|
851
|
+
} finally {
|
|
852
|
+
Error.prepareStackTrace = originalPrepare;
|
|
840
853
|
}
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
}).build();
|
|
844
|
-
var eventNotFoundError = error(
|
|
845
|
-
"runner.errors.eventNotFound"
|
|
846
|
-
).format(
|
|
847
|
-
({ id: id2 }) => `Event "${id2.toString()}" not found. Did you forget to register it?`
|
|
848
|
-
).build();
|
|
849
|
-
var resourceNotFoundError = error(
|
|
850
|
-
"runner.errors.resourceNotFound"
|
|
851
|
-
).format(
|
|
852
|
-
({ id: id2 }) => `Resource "${id2.toString()}" not found. Did you forget to register it or are you using the correct id?`
|
|
853
|
-
).build();
|
|
854
|
-
var middlewareNotRegisteredError = error("runner.errors.middlewareNotRegistered").format(
|
|
855
|
-
({ type, source, middlewareId }) => `Middleware inside ${type} "${source}" depends on "${middlewareId}" but it's not registered. Did you forget to register it?`
|
|
856
|
-
).build();
|
|
857
|
-
var tagNotFoundError = error(
|
|
858
|
-
"runner.errors.tagNotFound"
|
|
859
|
-
).format(
|
|
860
|
-
({ id: id2 }) => `Tag "${id2}" not registered. Did you forget to register it inside a resource?`
|
|
861
|
-
).build();
|
|
862
|
-
var lockedError = error(
|
|
863
|
-
"runner.errors.locked"
|
|
864
|
-
).format(
|
|
865
|
-
({ what }) => `Cannot modify the ${what.toString()} when it is locked.`
|
|
866
|
-
).build();
|
|
867
|
-
var storeAlreadyInitializedError = error(
|
|
868
|
-
"runner.errors.storeAlreadyInitialized"
|
|
869
|
-
).format(() => "Store already initialized. Cannot reinitialize.").build();
|
|
870
|
-
var validationError = error("runner.errors.validation").format(({ subject, id: id2, originalError }) => {
|
|
871
|
-
const errorMessage = originalError instanceof Error ? originalError.message : String(originalError);
|
|
872
|
-
return `${subject} validation failed for ${id2.toString()}: ${errorMessage}`;
|
|
873
|
-
}).build();
|
|
874
|
-
var eventCycleError = error("runner.errors.eventCycle").format(({ path }) => {
|
|
875
|
-
const chain = path.map((p) => `${p.id}\u2190${p.source}`).join(" -> ");
|
|
876
|
-
return `Event emission cycle detected:
|
|
877
|
-
${chain}
|
|
878
|
-
|
|
879
|
-
Break the cycle by changing hook logic (avoid mutual emits) or gate with conditions/tags.`;
|
|
880
|
-
}).build();
|
|
881
|
-
var eventEmissionCycleError = error("runner.errors.eventEmissionCycle").format(({ cycles }) => {
|
|
882
|
-
const list = cycles.map((c) => ` \u2022 ${c}`).join("\n");
|
|
883
|
-
return `Event emission cycles detected between hooks and events:
|
|
884
|
-
${list}
|
|
854
|
+
}
|
|
855
|
+
__name(getCallerFile, "getCallerFile");
|
|
885
856
|
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
857
|
+
// src/definers/defineTask.ts
|
|
858
|
+
function defineTask(taskConfig) {
|
|
859
|
+
const filePath = getCallerFile();
|
|
860
|
+
const id2 = taskConfig.id;
|
|
861
|
+
return {
|
|
862
|
+
[symbolTask]: true,
|
|
863
|
+
[symbolFilePath]: filePath,
|
|
864
|
+
id: id2,
|
|
865
|
+
dependencies: taskConfig.dependencies || {},
|
|
866
|
+
middleware: taskConfig.middleware || [],
|
|
867
|
+
run: taskConfig.run,
|
|
868
|
+
inputSchema: taskConfig.inputSchema,
|
|
869
|
+
resultSchema: taskConfig.resultSchema,
|
|
870
|
+
meta: taskConfig.meta || {},
|
|
871
|
+
tags: taskConfig.tags || [],
|
|
872
|
+
// autorun,
|
|
873
|
+
optional() {
|
|
874
|
+
return {
|
|
875
|
+
inner: this,
|
|
876
|
+
[symbolOptionalDependency]: true
|
|
877
|
+
};
|
|
878
|
+
}
|
|
879
|
+
};
|
|
880
|
+
}
|
|
881
|
+
__name(defineTask, "defineTask");
|
|
882
|
+
defineTask.phantom = (taskConfig) => {
|
|
883
|
+
const taskDef = defineTask({
|
|
884
|
+
...taskConfig,
|
|
885
|
+
run: /* @__PURE__ */ __name(async (input) => {
|
|
886
|
+
return void 0;
|
|
887
|
+
}, "run")
|
|
888
|
+
});
|
|
889
|
+
taskDef[symbolPhantomTask] = true;
|
|
890
|
+
return taskDef;
|
|
891
|
+
};
|
|
892
|
+
|
|
893
|
+
// src/definers/defineHook.ts
|
|
894
|
+
function defineHook(hookDef) {
|
|
895
|
+
const filePath = getCallerFile();
|
|
896
|
+
return {
|
|
897
|
+
[symbolHook]: true,
|
|
898
|
+
[symbolFilePath]: filePath,
|
|
899
|
+
id: hookDef.id,
|
|
900
|
+
dependencies: hookDef.dependencies || {},
|
|
901
|
+
on: hookDef.on,
|
|
902
|
+
order: hookDef.order,
|
|
903
|
+
run: hookDef.run,
|
|
904
|
+
meta: hookDef.meta || {},
|
|
905
|
+
tags: hookDef.tags || []
|
|
906
|
+
};
|
|
899
907
|
}
|
|
900
|
-
__name(
|
|
908
|
+
__name(defineHook, "defineHook");
|
|
901
909
|
|
|
902
910
|
// src/definers/defineResource.ts
|
|
903
911
|
function defineResource(constConfig) {
|
|
@@ -958,6 +966,7 @@ function defineEvent(config) {
|
|
|
958
966
|
[symbolEvent]: true,
|
|
959
967
|
// This is a workaround
|
|
960
968
|
tags: eventConfig.tags || [],
|
|
969
|
+
parallel: eventConfig.parallel,
|
|
961
970
|
optional() {
|
|
962
971
|
return {
|
|
963
972
|
inner: this,
|
|
@@ -3488,30 +3497,279 @@ var DependencyProcessor = class {
|
|
|
3488
3497
|
}
|
|
3489
3498
|
};
|
|
3490
3499
|
|
|
3491
|
-
// src/models/
|
|
3500
|
+
// src/models/event/types.ts
|
|
3492
3501
|
var HandlerOptionsDefaults = { order: 0 };
|
|
3493
|
-
|
|
3494
|
-
|
|
3495
|
-
|
|
3502
|
+
|
|
3503
|
+
// src/models/event/ListenerRegistry.ts
|
|
3504
|
+
var ListenerRegistry = class {
|
|
3505
|
+
constructor(isExcludedFromGlobal) {
|
|
3496
3506
|
this.listeners = /* @__PURE__ */ new Map();
|
|
3497
3507
|
this.globalListeners = [];
|
|
3498
|
-
// Caching system for merged listeners to improve performance
|
|
3499
3508
|
this.cachedMergedListeners = /* @__PURE__ */ new Map();
|
|
3500
|
-
this.
|
|
3501
|
-
|
|
3509
|
+
this._globalListenersCacheValid = true;
|
|
3510
|
+
this.isExcludedFromGlobal = isExcludedFromGlobal ?? ((event2) => globalTags.excludeFromGlobalHooks.exists(event2));
|
|
3511
|
+
}
|
|
3512
|
+
static {
|
|
3513
|
+
__name(this, "ListenerRegistry");
|
|
3514
|
+
}
|
|
3515
|
+
get globalListenersCacheValid() {
|
|
3516
|
+
return this._globalListenersCacheValid;
|
|
3517
|
+
}
|
|
3518
|
+
addListener(eventId, newListener) {
|
|
3519
|
+
const listeners = this.listeners.get(eventId);
|
|
3520
|
+
if (listeners) {
|
|
3521
|
+
this.insertListener(listeners, newListener);
|
|
3522
|
+
} else {
|
|
3523
|
+
this.listeners.set(eventId, [newListener]);
|
|
3524
|
+
}
|
|
3525
|
+
this.invalidateCache(eventId);
|
|
3526
|
+
}
|
|
3527
|
+
addGlobalListener(newListener) {
|
|
3528
|
+
this.insertListener(this.globalListeners, newListener);
|
|
3529
|
+
this.invalidateCache();
|
|
3530
|
+
}
|
|
3531
|
+
getListenersForEmit(eventDefinition) {
|
|
3532
|
+
const excludeGlobal = this.isExcludedFromGlobal(eventDefinition);
|
|
3533
|
+
if (excludeGlobal) {
|
|
3534
|
+
return this.listeners.get(eventDefinition.id) || [];
|
|
3535
|
+
}
|
|
3536
|
+
return this.getCachedMergedListeners(eventDefinition.id);
|
|
3537
|
+
}
|
|
3538
|
+
hasListeners(eventDefinition) {
|
|
3539
|
+
const eventListeners = this.listeners.get(eventDefinition.id) || [];
|
|
3540
|
+
if (eventListeners.length > 0) {
|
|
3541
|
+
return true;
|
|
3542
|
+
}
|
|
3543
|
+
if (this.globalListeners.length === 0) {
|
|
3544
|
+
return false;
|
|
3545
|
+
}
|
|
3546
|
+
return !this.isExcludedFromGlobal(eventDefinition);
|
|
3547
|
+
}
|
|
3548
|
+
/**
|
|
3549
|
+
* Cached merge between event-specific and global listeners.
|
|
3550
|
+
* Exposed for backward compatibility with existing tests.
|
|
3551
|
+
*/
|
|
3552
|
+
getCachedMergedListeners(eventId) {
|
|
3553
|
+
if (!this._globalListenersCacheValid) {
|
|
3554
|
+
this.cachedMergedListeners.clear();
|
|
3555
|
+
this._globalListenersCacheValid = true;
|
|
3556
|
+
}
|
|
3557
|
+
let cached = this.cachedMergedListeners.get(eventId);
|
|
3558
|
+
if (!cached) {
|
|
3559
|
+
const eventListeners = this.listeners.get(eventId) || [];
|
|
3560
|
+
if (eventListeners.length === 0 && this.globalListeners.length === 0) {
|
|
3561
|
+
cached = [];
|
|
3562
|
+
} else if (eventListeners.length === 0) {
|
|
3563
|
+
cached = this.globalListeners;
|
|
3564
|
+
} else if (this.globalListeners.length === 0) {
|
|
3565
|
+
cached = eventListeners;
|
|
3566
|
+
} else {
|
|
3567
|
+
cached = this.mergeSortedListeners(eventListeners, this.globalListeners);
|
|
3568
|
+
}
|
|
3569
|
+
this.cachedMergedListeners.set(eventId, cached);
|
|
3570
|
+
}
|
|
3571
|
+
return cached;
|
|
3572
|
+
}
|
|
3573
|
+
invalidateCache(eventId) {
|
|
3574
|
+
if (eventId) {
|
|
3575
|
+
this.cachedMergedListeners.delete(eventId);
|
|
3576
|
+
} else {
|
|
3577
|
+
this._globalListenersCacheValid = false;
|
|
3578
|
+
}
|
|
3579
|
+
}
|
|
3580
|
+
mergeSortedListeners(a, b) {
|
|
3581
|
+
const result = [];
|
|
3582
|
+
let i = 0;
|
|
3583
|
+
let j = 0;
|
|
3584
|
+
while (i < a.length && j < b.length) {
|
|
3585
|
+
if (a[i].order <= b[j].order) {
|
|
3586
|
+
result.push(a[i++]);
|
|
3587
|
+
} else {
|
|
3588
|
+
result.push(b[j++]);
|
|
3589
|
+
}
|
|
3590
|
+
}
|
|
3591
|
+
while (i < a.length) result.push(a[i++]);
|
|
3592
|
+
while (j < b.length) result.push(b[j++]);
|
|
3593
|
+
return result;
|
|
3594
|
+
}
|
|
3595
|
+
insertListener(listeners, newListener) {
|
|
3596
|
+
let low = 0;
|
|
3597
|
+
let high = listeners.length;
|
|
3598
|
+
while (low < high) {
|
|
3599
|
+
const mid = low + high >>> 1;
|
|
3600
|
+
if (listeners[mid].order < newListener.order) {
|
|
3601
|
+
low = mid + 1;
|
|
3602
|
+
} else {
|
|
3603
|
+
high = mid;
|
|
3604
|
+
}
|
|
3605
|
+
}
|
|
3606
|
+
listeners.splice(low, 0, newListener);
|
|
3607
|
+
}
|
|
3608
|
+
};
|
|
3609
|
+
function createListener(newListener) {
|
|
3610
|
+
return {
|
|
3611
|
+
handler: newListener.handler,
|
|
3612
|
+
order: newListener.order ?? HandlerOptionsDefaults.order,
|
|
3613
|
+
filter: newListener.filter,
|
|
3614
|
+
id: newListener.id,
|
|
3615
|
+
isGlobal: newListener.isGlobal ?? false
|
|
3616
|
+
};
|
|
3617
|
+
}
|
|
3618
|
+
__name(createListener, "createListener");
|
|
3619
|
+
|
|
3620
|
+
// src/models/event/InterceptorPipeline.ts
|
|
3621
|
+
function composeInterceptors(interceptors, base) {
|
|
3622
|
+
return interceptors.slice().reverse().reduce(
|
|
3623
|
+
(next, interceptor) => (...args) => interceptor(next, ...args),
|
|
3624
|
+
base
|
|
3625
|
+
);
|
|
3626
|
+
}
|
|
3627
|
+
__name(composeInterceptors, "composeInterceptors");
|
|
3628
|
+
|
|
3629
|
+
// src/models/event/EmissionExecutor.ts
|
|
3630
|
+
async function executeSequentially({
|
|
3631
|
+
listeners,
|
|
3632
|
+
event: event2,
|
|
3633
|
+
isPropagationStopped
|
|
3634
|
+
}) {
|
|
3635
|
+
for (const listener of listeners) {
|
|
3636
|
+
if (isPropagationStopped()) {
|
|
3637
|
+
break;
|
|
3638
|
+
}
|
|
3639
|
+
if (shouldExecuteListener(listener, event2)) {
|
|
3640
|
+
await listener.handler(event2);
|
|
3641
|
+
}
|
|
3642
|
+
}
|
|
3643
|
+
}
|
|
3644
|
+
__name(executeSequentially, "executeSequentially");
|
|
3645
|
+
async function executeInParallel({
|
|
3646
|
+
listeners,
|
|
3647
|
+
event: event2
|
|
3648
|
+
}) {
|
|
3649
|
+
if (listeners.length === 0 || event2.isPropagationStopped()) {
|
|
3650
|
+
return;
|
|
3651
|
+
}
|
|
3652
|
+
let currentOrder = listeners[0].order;
|
|
3653
|
+
let currentBatch = [];
|
|
3654
|
+
const executeBatch = /* @__PURE__ */ __name(async (batch) => {
|
|
3655
|
+
const results = await Promise.allSettled(
|
|
3656
|
+
batch.map(async (listener) => {
|
|
3657
|
+
if (shouldExecuteListener(listener, event2)) {
|
|
3658
|
+
await listener.handler(event2);
|
|
3659
|
+
}
|
|
3660
|
+
})
|
|
3661
|
+
);
|
|
3662
|
+
const errors = results.map((result, index) => ({ result, listener: batch[index] })).filter(
|
|
3663
|
+
(r2) => r2.result.status === "rejected"
|
|
3664
|
+
).map(({ result, listener }) => {
|
|
3665
|
+
const reason = result.reason;
|
|
3666
|
+
const errObj = reason && typeof reason === "object" ? reason : new Error(String(reason));
|
|
3667
|
+
if (errObj.listenerId === void 0) {
|
|
3668
|
+
errObj.listenerId = listener.id;
|
|
3669
|
+
}
|
|
3670
|
+
if (errObj.listenerOrder === void 0) {
|
|
3671
|
+
errObj.listenerOrder = listener.order;
|
|
3672
|
+
}
|
|
3673
|
+
return errObj;
|
|
3674
|
+
});
|
|
3675
|
+
if (errors.length > 0) {
|
|
3676
|
+
if (errors.length === 1) {
|
|
3677
|
+
throw errors[0];
|
|
3678
|
+
}
|
|
3679
|
+
const aggregateError = new Error(
|
|
3680
|
+
`${errors.length} listeners failed in parallel batch`
|
|
3681
|
+
);
|
|
3682
|
+
aggregateError.errors = errors;
|
|
3683
|
+
aggregateError.name = "AggregateError";
|
|
3684
|
+
throw aggregateError;
|
|
3685
|
+
}
|
|
3686
|
+
}, "executeBatch");
|
|
3687
|
+
for (const listener of listeners) {
|
|
3688
|
+
if (listener.order !== currentOrder) {
|
|
3689
|
+
await executeBatch(currentBatch);
|
|
3690
|
+
currentBatch = [];
|
|
3691
|
+
currentOrder = listener.order;
|
|
3692
|
+
if (event2.isPropagationStopped()) {
|
|
3693
|
+
break;
|
|
3694
|
+
}
|
|
3695
|
+
}
|
|
3696
|
+
currentBatch.push(listener);
|
|
3697
|
+
}
|
|
3698
|
+
if (currentBatch.length > 0 && !event2.isPropagationStopped()) {
|
|
3699
|
+
await executeBatch(currentBatch);
|
|
3700
|
+
}
|
|
3701
|
+
}
|
|
3702
|
+
__name(executeInParallel, "executeInParallel");
|
|
3703
|
+
function shouldExecuteListener(listener, event2) {
|
|
3704
|
+
if (listener.id && listener.id === event2.source) {
|
|
3705
|
+
return false;
|
|
3706
|
+
}
|
|
3707
|
+
return !listener.filter || listener.filter(event2);
|
|
3708
|
+
}
|
|
3709
|
+
__name(shouldExecuteListener, "shouldExecuteListener");
|
|
3710
|
+
|
|
3711
|
+
// src/models/event/CycleContext.ts
|
|
3712
|
+
var CycleContext = class {
|
|
3713
|
+
static {
|
|
3714
|
+
__name(this, "CycleContext");
|
|
3715
|
+
}
|
|
3716
|
+
constructor(runtimeCycleDetection) {
|
|
3717
|
+
const platform3 = getPlatform();
|
|
3718
|
+
if (platform3.hasAsyncLocalStorage() && runtimeCycleDetection) {
|
|
3719
|
+
this.emissionStack = platform3.createAsyncLocalStorage();
|
|
3720
|
+
this.currentHookIdContext = platform3.createAsyncLocalStorage();
|
|
3721
|
+
this.isEnabled = true;
|
|
3722
|
+
} else {
|
|
3723
|
+
this.emissionStack = null;
|
|
3724
|
+
this.currentHookIdContext = null;
|
|
3725
|
+
this.isEnabled = false;
|
|
3726
|
+
}
|
|
3727
|
+
}
|
|
3728
|
+
runEmission(frame, source, processEmission) {
|
|
3729
|
+
if (!this.isEnabled || !this.emissionStack || !this.currentHookIdContext) {
|
|
3730
|
+
return processEmission();
|
|
3731
|
+
}
|
|
3732
|
+
const currentStack = this.emissionStack.getStore();
|
|
3733
|
+
if (currentStack) {
|
|
3734
|
+
const cycleStart = currentStack.findIndex(
|
|
3735
|
+
(f) => f.id === frame.id
|
|
3736
|
+
);
|
|
3737
|
+
if (cycleStart !== -1) {
|
|
3738
|
+
const top = currentStack[currentStack.length - 1];
|
|
3739
|
+
const currentHookId = this.currentHookIdContext.getStore();
|
|
3740
|
+
const safeReEmitBySameHook = top.id === frame.id && currentHookId && currentHookId === source;
|
|
3741
|
+
if (!safeReEmitBySameHook) {
|
|
3742
|
+
eventCycleError.throw({
|
|
3743
|
+
path: [...currentStack.slice(cycleStart), frame]
|
|
3744
|
+
});
|
|
3745
|
+
}
|
|
3746
|
+
}
|
|
3747
|
+
}
|
|
3748
|
+
const nextStack = currentStack ? [...currentStack, frame] : [frame];
|
|
3749
|
+
return this.emissionStack.run(nextStack, processEmission);
|
|
3750
|
+
}
|
|
3751
|
+
runHook(hookId, execute) {
|
|
3752
|
+
if (!this.isEnabled || !this.currentHookIdContext) {
|
|
3753
|
+
return execute();
|
|
3754
|
+
}
|
|
3755
|
+
return this.currentHookIdContext.run(hookId, execute);
|
|
3756
|
+
}
|
|
3757
|
+
};
|
|
3758
|
+
|
|
3759
|
+
// src/models/EventManager.ts
|
|
3760
|
+
var EventManager = class {
|
|
3761
|
+
constructor(options) {
|
|
3762
|
+
// Interceptors storage (tests access these directly)
|
|
3502
3763
|
this.emissionInterceptors = [];
|
|
3503
3764
|
this.hookInterceptors = [];
|
|
3504
3765
|
// Locking mechanism to prevent modifications after initialization
|
|
3505
3766
|
this.#isLocked = false;
|
|
3506
3767
|
this.runtimeCycleDetection = options?.runtimeCycleDetection ?? true;
|
|
3507
|
-
|
|
3508
|
-
|
|
3509
|
-
|
|
3510
|
-
|
|
3511
|
-
|
|
3512
|
-
this.emissionStack = null;
|
|
3513
|
-
this.currentHookIdContext = null;
|
|
3514
|
-
}
|
|
3768
|
+
this.registry = new ListenerRegistry();
|
|
3769
|
+
this.cycleContext = new CycleContext(this.runtimeCycleDetection);
|
|
3770
|
+
this.listeners = this.registry.listeners;
|
|
3771
|
+
this.globalListeners = this.registry.globalListeners;
|
|
3772
|
+
this.cachedMergedListeners = this.registry.cachedMergedListeners;
|
|
3515
3773
|
}
|
|
3516
3774
|
static {
|
|
3517
3775
|
__name(this, "EventManager");
|
|
@@ -3552,8 +3810,7 @@ var EventManager = class {
|
|
|
3552
3810
|
}
|
|
3553
3811
|
const frame = { id: eventDefinition.id, source };
|
|
3554
3812
|
const processEmission = /* @__PURE__ */ __name(async () => {
|
|
3555
|
-
const
|
|
3556
|
-
const allListeners = excludeFromGlobal ? this.listeners.get(eventDefinition.id) || [] : this.getCachedMergedListeners(eventDefinition.id);
|
|
3813
|
+
const allListeners = this.registry.getListenersForEmit(eventDefinition);
|
|
3557
3814
|
let propagationStopped = false;
|
|
3558
3815
|
const event2 = {
|
|
3559
3816
|
id: eventDefinition.id,
|
|
@@ -3571,49 +3828,23 @@ var EventManager = class {
|
|
|
3571
3828
|
if (allListeners.length === 0) {
|
|
3572
3829
|
return;
|
|
3573
3830
|
}
|
|
3574
|
-
|
|
3575
|
-
|
|
3576
|
-
|
|
3577
|
-
|
|
3578
|
-
|
|
3579
|
-
|
|
3580
|
-
|
|
3581
|
-
}
|
|
3582
|
-
if (!listener.filter || listener.filter(eventToEmit)) {
|
|
3583
|
-
await listener.handler(eventToEmit);
|
|
3584
|
-
}
|
|
3831
|
+
if (eventDefinition.parallel) {
|
|
3832
|
+
await executeInParallel({ listeners: allListeners, event: eventToEmit });
|
|
3833
|
+
} else {
|
|
3834
|
+
await executeSequentially({
|
|
3835
|
+
listeners: allListeners,
|
|
3836
|
+
event: eventToEmit,
|
|
3837
|
+
isPropagationStopped: /* @__PURE__ */ __name(() => propagationStopped, "isPropagationStopped")
|
|
3838
|
+
});
|
|
3585
3839
|
}
|
|
3586
3840
|
}, "baseEmit");
|
|
3587
|
-
|
|
3588
|
-
|
|
3589
|
-
|
|
3590
|
-
|
|
3591
|
-
emitWithInterceptors = /* @__PURE__ */ __name(async (eventToEmit) => interceptor(nextFunction, eventToEmit), "emitWithInterceptors");
|
|
3592
|
-
}
|
|
3841
|
+
const emitWithInterceptors = composeInterceptors(
|
|
3842
|
+
this.emissionInterceptors,
|
|
3843
|
+
baseEmit
|
|
3844
|
+
);
|
|
3593
3845
|
await emitWithInterceptors(event2);
|
|
3594
3846
|
}, "processEmission");
|
|
3595
|
-
|
|
3596
|
-
const currentStack = this.emissionStack.getStore();
|
|
3597
|
-
if (currentStack) {
|
|
3598
|
-
const cycleStart = currentStack.findIndex(
|
|
3599
|
-
(f) => f.id === frame.id
|
|
3600
|
-
);
|
|
3601
|
-
if (cycleStart !== -1) {
|
|
3602
|
-
const top = currentStack[currentStack.length - 1];
|
|
3603
|
-
const currentHookId = this.currentHookIdContext.getStore();
|
|
3604
|
-
const safeReEmitBySameHook = top.id === frame.id && currentHookId && currentHookId === source;
|
|
3605
|
-
if (!safeReEmitBySameHook) {
|
|
3606
|
-
eventCycleError.throw({
|
|
3607
|
-
path: [...currentStack.slice(cycleStart), frame]
|
|
3608
|
-
});
|
|
3609
|
-
}
|
|
3610
|
-
}
|
|
3611
|
-
}
|
|
3612
|
-
const nextStack = currentStack ? [...currentStack, frame] : [frame];
|
|
3613
|
-
await this.emissionStack.run(nextStack, processEmission);
|
|
3614
|
-
} else {
|
|
3615
|
-
await processEmission();
|
|
3616
|
-
}
|
|
3847
|
+
await this.cycleContext.runEmission(frame, source, processEmission);
|
|
3617
3848
|
}
|
|
3618
3849
|
/**
|
|
3619
3850
|
* Registers an event listener for specific event(s).
|
|
@@ -3625,24 +3856,18 @@ var EventManager = class {
|
|
|
3625
3856
|
*/
|
|
3626
3857
|
addListener(event2, handler, options = HandlerOptionsDefaults) {
|
|
3627
3858
|
this.checkLock();
|
|
3628
|
-
const newListener = {
|
|
3859
|
+
const newListener = createListener({
|
|
3629
3860
|
handler,
|
|
3630
|
-
order: options.order
|
|
3861
|
+
order: options.order,
|
|
3631
3862
|
filter: options.filter,
|
|
3632
3863
|
id: options.id,
|
|
3633
3864
|
isGlobal: false
|
|
3634
|
-
};
|
|
3865
|
+
});
|
|
3635
3866
|
if (Array.isArray(event2)) {
|
|
3636
3867
|
event2.forEach((id2) => this.addListener(id2, handler, options));
|
|
3637
3868
|
} else {
|
|
3638
3869
|
const eventId = event2.id;
|
|
3639
|
-
|
|
3640
|
-
if (listeners) {
|
|
3641
|
-
this.insertListener(listeners, newListener);
|
|
3642
|
-
} else {
|
|
3643
|
-
this.listeners.set(eventId, [newListener]);
|
|
3644
|
-
}
|
|
3645
|
-
this.invalidateCache(eventId);
|
|
3870
|
+
this.registry.addListener(eventId, newListener);
|
|
3646
3871
|
}
|
|
3647
3872
|
}
|
|
3648
3873
|
/**
|
|
@@ -3654,15 +3879,14 @@ var EventManager = class {
|
|
|
3654
3879
|
*/
|
|
3655
3880
|
addGlobalListener(handler, options = HandlerOptionsDefaults) {
|
|
3656
3881
|
this.checkLock();
|
|
3657
|
-
const newListener = {
|
|
3882
|
+
const newListener = createListener({
|
|
3658
3883
|
handler,
|
|
3659
|
-
order: options.order
|
|
3884
|
+
order: options.order,
|
|
3660
3885
|
filter: options.filter,
|
|
3661
3886
|
id: options.id,
|
|
3662
3887
|
isGlobal: true
|
|
3663
|
-
};
|
|
3664
|
-
this.
|
|
3665
|
-
this.invalidateCache();
|
|
3888
|
+
});
|
|
3889
|
+
this.registry.addGlobalListener(newListener);
|
|
3666
3890
|
}
|
|
3667
3891
|
/**
|
|
3668
3892
|
* Checks if there are any listeners registered for the given event
|
|
@@ -3671,15 +3895,7 @@ var EventManager = class {
|
|
|
3671
3895
|
* @returns true if listeners exist, false otherwise
|
|
3672
3896
|
*/
|
|
3673
3897
|
hasListeners(eventDefinition) {
|
|
3674
|
-
|
|
3675
|
-
if (eventListeners.length > 0) {
|
|
3676
|
-
return true;
|
|
3677
|
-
}
|
|
3678
|
-
if (this.globalListeners.length === 0) {
|
|
3679
|
-
return false;
|
|
3680
|
-
}
|
|
3681
|
-
const isExcludedFromGlobal = globalTags.excludeFromGlobalHooks.exists(eventDefinition);
|
|
3682
|
-
return !isExcludedFromGlobal;
|
|
3898
|
+
return this.registry.hasListeners(eventDefinition);
|
|
3683
3899
|
}
|
|
3684
3900
|
/**
|
|
3685
3901
|
* Adds an interceptor for all event emissions
|
|
@@ -3724,20 +3940,14 @@ var EventManager = class {
|
|
|
3724
3940
|
throw err;
|
|
3725
3941
|
}
|
|
3726
3942
|
}, "baseExecute");
|
|
3727
|
-
|
|
3728
|
-
|
|
3729
|
-
|
|
3730
|
-
|
|
3731
|
-
|
|
3732
|
-
|
|
3733
|
-
|
|
3734
|
-
|
|
3735
|
-
hook2.id,
|
|
3736
|
-
async () => await executeWithInterceptors(hook2, event2)
|
|
3737
|
-
);
|
|
3738
|
-
} else {
|
|
3739
|
-
return await executeWithInterceptors(hook2, event2);
|
|
3740
|
-
}
|
|
3943
|
+
const executeWithInterceptors = composeInterceptors(
|
|
3944
|
+
this.hookInterceptors,
|
|
3945
|
+
baseExecute
|
|
3946
|
+
);
|
|
3947
|
+
return this.cycleContext.isEnabled ? await this.cycleContext.runHook(
|
|
3948
|
+
hook2.id,
|
|
3949
|
+
() => executeWithInterceptors(hook2, event2)
|
|
3950
|
+
) : await executeWithInterceptors(hook2, event2);
|
|
3741
3951
|
}
|
|
3742
3952
|
// ==================== PRIVATE METHODS ====================
|
|
3743
3953
|
/**
|
|
@@ -3748,102 +3958,12 @@ var EventManager = class {
|
|
|
3748
3958
|
lockedError.throw({ what: "EventManager" });
|
|
3749
3959
|
}
|
|
3750
3960
|
}
|
|
3751
|
-
/**
|
|
3752
|
-
* Merges two sorted arrays of listeners while maintaining order.
|
|
3753
|
-
* Used to combine event-specific listeners with global listeners.
|
|
3754
|
-
*
|
|
3755
|
-
* @param a - First array of listeners
|
|
3756
|
-
* @param b - Second array of listeners
|
|
3757
|
-
* @returns Merged and sorted array of listeners
|
|
3758
|
-
*/
|
|
3759
|
-
mergeSortedListeners(a, b) {
|
|
3760
|
-
const result = [];
|
|
3761
|
-
let i = 0, j = 0;
|
|
3762
|
-
while (i < a.length && j < b.length) {
|
|
3763
|
-
if (a[i].order <= b[j].order) {
|
|
3764
|
-
result.push(a[i++]);
|
|
3765
|
-
} else {
|
|
3766
|
-
result.push(b[j++]);
|
|
3767
|
-
}
|
|
3768
|
-
}
|
|
3769
|
-
while (i < a.length) result.push(a[i++]);
|
|
3770
|
-
while (j < b.length) result.push(b[j++]);
|
|
3771
|
-
return result;
|
|
3772
|
-
}
|
|
3773
|
-
/**
|
|
3774
|
-
* Inserts a new listener into a sorted array using binary search.
|
|
3775
|
-
* Maintains order based on listener priority.
|
|
3776
|
-
*
|
|
3777
|
-
* @param listeners - Array to insert into
|
|
3778
|
-
* @param newListener - Listener to insert
|
|
3779
|
-
*/
|
|
3780
|
-
insertListener(listeners, newListener) {
|
|
3781
|
-
let low = 0;
|
|
3782
|
-
let high = listeners.length;
|
|
3783
|
-
while (low < high) {
|
|
3784
|
-
const mid = low + high >>> 1;
|
|
3785
|
-
if (listeners[mid].order < newListener.order) {
|
|
3786
|
-
low = mid + 1;
|
|
3787
|
-
} else {
|
|
3788
|
-
high = mid;
|
|
3789
|
-
}
|
|
3790
|
-
}
|
|
3791
|
-
listeners.splice(low, 0, newListener);
|
|
3792
|
-
}
|
|
3793
|
-
/**
|
|
3794
|
-
* Returns true if the given emission carries the tag that marks
|
|
3795
|
-
* it as excluded from global ("*") listeners.
|
|
3796
|
-
*
|
|
3797
|
-
* @param event - The event emission to check
|
|
3798
|
-
* @returns true if event should exclude global listeners
|
|
3799
|
-
*/
|
|
3800
|
-
isExcludedFromGlobal(event2) {
|
|
3801
|
-
return globalTags.excludeFromGlobalHooks.exists(event2);
|
|
3802
|
-
}
|
|
3803
3961
|
/**
|
|
3804
3962
|
* Retrieves cached merged listeners for an event, or creates them if not cached.
|
|
3805
|
-
*
|
|
3806
|
-
*
|
|
3807
|
-
* @param eventId - The event ID to get listeners for
|
|
3808
|
-
* @returns Array of merged listeners sorted by priority
|
|
3963
|
+
* Kept for backward compatibility (tests spy on this).
|
|
3809
3964
|
*/
|
|
3810
3965
|
getCachedMergedListeners(eventId) {
|
|
3811
|
-
|
|
3812
|
-
this.cachedMergedListeners.clear();
|
|
3813
|
-
this.globalListenersCacheValid = true;
|
|
3814
|
-
}
|
|
3815
|
-
let cached = this.cachedMergedListeners.get(eventId);
|
|
3816
|
-
if (!cached) {
|
|
3817
|
-
const eventListeners = this.listeners.get(eventId) || [];
|
|
3818
|
-
if (eventListeners.length === 0 && this.globalListeners.length === 0) {
|
|
3819
|
-
cached = [];
|
|
3820
|
-
} else if (eventListeners.length === 0) {
|
|
3821
|
-
cached = this.globalListeners;
|
|
3822
|
-
} else if (this.globalListeners.length === 0) {
|
|
3823
|
-
cached = eventListeners;
|
|
3824
|
-
} else {
|
|
3825
|
-
cached = this.mergeSortedListeners(
|
|
3826
|
-
eventListeners,
|
|
3827
|
-
this.globalListeners
|
|
3828
|
-
);
|
|
3829
|
-
}
|
|
3830
|
-
this.cachedMergedListeners.set(eventId, cached);
|
|
3831
|
-
}
|
|
3832
|
-
return cached;
|
|
3833
|
-
}
|
|
3834
|
-
/**
|
|
3835
|
-
* Invalidates the cached merged listeners.
|
|
3836
|
-
* If eventId is provided, only invalidates cache for that specific event.
|
|
3837
|
-
* Otherwise, invalidates the global cache.
|
|
3838
|
-
*
|
|
3839
|
-
* @param eventId - Optional specific event ID to invalidate
|
|
3840
|
-
*/
|
|
3841
|
-
invalidateCache(eventId) {
|
|
3842
|
-
if (eventId) {
|
|
3843
|
-
this.cachedMergedListeners.delete(eventId);
|
|
3844
|
-
} else {
|
|
3845
|
-
this.globalListenersCacheValid = false;
|
|
3846
|
-
}
|
|
3966
|
+
return this.registry.getCachedMergedListeners(eventId);
|
|
3847
3967
|
}
|
|
3848
3968
|
};
|
|
3849
3969
|
|
|
@@ -5789,6 +5909,10 @@ function makeEventBuilder(state) {
|
|
|
5789
5909
|
const next = clone5(state, { meta: m });
|
|
5790
5910
|
return makeEventBuilder(next);
|
|
5791
5911
|
},
|
|
5912
|
+
parallel(enabled = true) {
|
|
5913
|
+
const next = clone5(state, { parallel: enabled });
|
|
5914
|
+
return makeEventBuilder(next);
|
|
5915
|
+
},
|
|
5792
5916
|
build() {
|
|
5793
5917
|
const event2 = defineEvent({
|
|
5794
5918
|
...state
|
|
@@ -5807,7 +5931,8 @@ function eventBuilder(id2) {
|
|
|
5807
5931
|
filePath,
|
|
5808
5932
|
meta: {},
|
|
5809
5933
|
payloadSchema: void 0,
|
|
5810
|
-
tags: []
|
|
5934
|
+
tags: [],
|
|
5935
|
+
parallel: void 0
|
|
5811
5936
|
});
|
|
5812
5937
|
return makeEventBuilder(initial);
|
|
5813
5938
|
}
|