@dudousxd/nestjs-durable 0.25.0 → 0.27.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/index.cjs CHANGED
@@ -24,28 +24,32 @@ __export(index_exports, {
24
24
  CONTEXT_ACCESSOR: () => CONTEXT_ACCESSOR,
25
25
  DEAD_LETTER_METADATA: () => DEAD_LETTER_METADATA,
26
26
  DURABLE_STEP_METADATA: () => DURABLE_STEP_METADATA,
27
- DURABLE_WORKER_OPTIONS: () => DURABLE_WORKER_OPTIONS,
28
27
  DURABLE_WORKER_RUNNERS: () => DURABLE_WORKER_RUNNERS,
29
28
  DeadLetter: () => DeadLetter,
30
29
  DurableModule: () => DurableModule,
30
+ DurableStartClient: () => DurableStartClient,
31
31
  DurableStep: () => DurableStep,
32
- DurableWorkerModule: () => DurableWorkerModule,
33
32
  ENTITY_METADATA: () => ENTITY_METADATA,
34
33
  ENTITY_ON_METADATA: () => ENTITY_ON_METADATA,
35
34
  Entity: () => Entity,
36
35
  EntityService: () => EntityService,
37
36
  IN_APP_RUN_REDIS_WORKER: () => IN_APP_RUN_REDIS_WORKER,
38
37
  IN_APP_WORKER_BINDING: () => IN_APP_WORKER_BINDING,
39
- IN_APP_WORKER_OPTIONS: () => IN_APP_WORKER_OPTIONS,
40
38
  IN_APP_WORKER_RUNNERS: () => IN_APP_WORKER_RUNNERS,
41
39
  IN_APP_WORKER_RUNTIME: () => IN_APP_WORKER_RUNTIME,
42
40
  InAppWorkerBootstrap: () => InAppWorkerBootstrap,
43
41
  ON_EVENT_METADATA: () => ON_EVENT_METADATA,
44
42
  On: () => On,
45
43
  OnEvent: () => OnEvent,
44
+ ProxyRunGateway: () => ProxyRunGateway,
45
+ RUN_GATEWAY: () => RUN_GATEWAY,
46
46
  RUN_REDIS_WORKER: () => RUN_REDIS_WORKER,
47
+ RunRequestResponder: () => RunRequestResponder,
47
48
  STEP_INTERCEPTOR_METADATA: () => STEP_INTERCEPTOR_METADATA,
49
+ Step: () => Step,
48
50
  StepInterceptor: () => StepInterceptor,
51
+ StoreRunGateway: () => StoreRunGateway,
52
+ TenantEventRepublisher: () => TenantEventRepublisher,
49
53
  ThinStepRegistrar: () => ThinStepRegistrar,
50
54
  ThinWorkerBootstrap: () => ThinWorkerBootstrap,
51
55
  ThinWorkflowRegistrar: () => ThinWorkflowRegistrar,
@@ -59,7 +63,11 @@ __export(index_exports, {
59
63
  getWorkflowMeta: () => getWorkflowMeta,
60
64
  inAppWorkerProviders: () => inAppWorkerProviders,
61
65
  isDeadLetterHandler: () => isDeadLetterHandler,
62
- isStepInterceptor: () => isStepInterceptor
66
+ isDrivingOperator: () => isDrivingOperator,
67
+ isOperatorRole: () => isOperatorRole,
68
+ isStepInterceptor: () => isStepInterceptor,
69
+ thinWorkerProviders: () => thinWorkerProviders,
70
+ unavailableRunGateway: () => unavailableRunGateway
63
71
  });
64
72
  module.exports = __toCommonJS(index_exports);
65
73
 
@@ -95,16 +103,41 @@ function getWorkflowMeta(target) {
95
103
  }
96
104
  __name(getWorkflowMeta, "getWorkflowMeta");
97
105
  var DURABLE_STEP_METADATA = Symbol("nestjs-durable:step-handler");
98
- function DurableStep(name) {
99
- return (_target, _propertyKey, descriptor) => {
106
+ function stepConfigFrom(options) {
107
+ const config = {
108
+ retries: options.retries,
109
+ backoff: options.backoff,
110
+ backoffMs: options.backoffMs,
111
+ backoffMaxMs: options.backoffMaxMs,
112
+ jitter: options.jitter,
113
+ timeoutMs: options.timeoutMs
114
+ };
115
+ const hasAnyField = Object.values(config).some((value) => value !== void 0);
116
+ return hasAnyField ? config : void 0;
117
+ }
118
+ __name(stepConfigFrom, "stepConfigFrom");
119
+ function Step(nameOrOptions) {
120
+ return (target, propertyKey, descriptor) => {
121
+ const options = typeof nameOrOptions === "string" ? {
122
+ name: nameOrOptions
123
+ } : nameOrOptions ?? {};
124
+ const derivedName = options.name ?? `${target.constructor.name}.${String(propertyKey)}`;
100
125
  const meta = {
101
- name
126
+ name: derivedName,
127
+ input: options.input,
128
+ output: options.output
102
129
  };
103
130
  Reflect.defineMetadata(DURABLE_STEP_METADATA, meta, descriptor.value);
131
+ descriptor.value[import_nestjs_durable_core.DURABLE_STEP_NAME] = derivedName;
132
+ const config = stepConfigFrom(options);
133
+ if (config !== void 0) {
134
+ descriptor.value[import_nestjs_durable_core.DURABLE_STEP_CONFIG] = config;
135
+ }
104
136
  return descriptor;
105
137
  };
106
138
  }
107
- __name(DurableStep, "DurableStep");
139
+ __name(Step, "Step");
140
+ var DurableStep = Step;
108
141
  function getDurableStepMeta(method) {
109
142
  return Reflect.getMetadata(DURABLE_STEP_METADATA, method);
110
143
  }
@@ -143,9 +176,105 @@ function getOnEvents(meta, target) {
143
176
  }
144
177
  __name(getOnEvents, "getOnEvents");
145
178
 
146
- // src/durable-worker.module.ts
179
+ // src/durable-start-client.ts
147
180
  var import_durable_worker = require("@dudousxd/durable-worker");
181
+ var import_nestjs_durable_core2 = require("@dudousxd/nestjs-durable-core");
148
182
  var import_common = require("@nestjs/common");
183
+ function _ts_decorate(decorators, target, key, desc) {
184
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
185
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
186
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
187
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
188
+ }
189
+ __name(_ts_decorate, "_ts_decorate");
190
+ function _ts_metadata(k, v) {
191
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
192
+ }
193
+ __name(_ts_metadata, "_ts_metadata");
194
+ var DurableStartClient = class {
195
+ static {
196
+ __name(this, "DurableStartClient");
197
+ }
198
+ options;
199
+ deps;
200
+ tenant;
201
+ constructor(options, deps) {
202
+ this.options = options;
203
+ this.deps = deps;
204
+ this.tenant = options.partition ?? "default";
205
+ }
206
+ async start(workflow, input, runId = globalThis.crypto.randomUUID(), opts) {
207
+ const name = (0, import_nestjs_durable_core2.workflowName)(workflow);
208
+ await (0, import_durable_worker.startRun)(this.options.connection, {
209
+ tenant: this.tenant,
210
+ workflow: name,
211
+ input,
212
+ runId,
213
+ // Option B: DO NOT pass `namespace` — the start-run queue stays the shared
214
+ // `durable-start-run` the operator consumes; tenant rides only as message data.
215
+ ...this.options.prefix !== void 0 ? {
216
+ prefix: this.options.prefix
217
+ } : {},
218
+ ...opts?.tags !== void 0 ? {
219
+ tags: opts.tags
220
+ } : {},
221
+ ...opts?.searchAttributes !== void 0 ? {
222
+ searchAttributes: opts.searchAttributes
223
+ } : {},
224
+ ...this.deps !== void 0 ? {
225
+ deps: this.deps
226
+ } : {}
227
+ });
228
+ return {
229
+ runId,
230
+ status: "pending"
231
+ };
232
+ }
233
+ cancel(_runId) {
234
+ return tenantUnsupported("cancel");
235
+ }
236
+ deleteRun(_runId) {
237
+ return tenantUnsupported("deleteRun");
238
+ }
239
+ // — everything below rejects: a tenant worker holds no store/driver, only the start channel. —
240
+ // The remaining WorkflowEngine surface WorkflowService delegates to (resume/waitForRun/signal/
241
+ // signalWithStart/publishEvent) all need the store or driver a tenant does not have. A tenant only
242
+ // ever calls `start`; these exist so a mistaken call fails with a CLEAR, named tenant error instead
243
+ // of a cryptic `this.engine.X is not a function` — the facade is honest about what it cannot do.
244
+ // Params mirror the WorkflowEngine surface being faced; every method rejects without reading them.
245
+ resume(_runId) {
246
+ return tenantUnsupported("resume");
247
+ }
248
+ waitForRun(_runId, _opts) {
249
+ return tenantUnsupported("waitForRun");
250
+ }
251
+ signal(_token, _payload) {
252
+ return tenantUnsupported("signal");
253
+ }
254
+ signalWithStart(_workflow, _input, _runId, _signal, _opts) {
255
+ return tenantUnsupported("signalWithStart");
256
+ }
257
+ publishEvent(_name, _payload, _opts) {
258
+ return tenantUnsupported("publishEvent");
259
+ }
260
+ };
261
+ DurableStartClient = _ts_decorate([
262
+ (0, import_common.Injectable)(),
263
+ _ts_metadata("design:type", Function),
264
+ _ts_metadata("design:paramtypes", [
265
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions,
266
+ typeof StartRunDeps === "undefined" ? Object : StartRunDeps
267
+ ])
268
+ ], DurableStartClient);
269
+ function tenantUnsupported(method) {
270
+ return Promise.reject(new Error(`${method}() is not available on a tenant worker (no store). Use the control plane for it.`));
271
+ }
272
+ __name(tenantUnsupported, "tenantUnsupported");
273
+
274
+ // src/durable-worker.module.ts
275
+ var import_durable_worker2 = require("@dudousxd/durable-worker");
276
+ var import_nestjs_durable_core3 = require("@dudousxd/nestjs-durable-core");
277
+ var import_common2 = require("@nestjs/common");
149
278
  var import_core = require("@nestjs/core");
150
279
 
151
280
  // src/discovery-helpers.ts
@@ -173,7 +302,12 @@ function scanSteps(discovery, scanner, register) {
173
302
  if (typeof method !== "function") continue;
174
303
  const meta = getDurableStepMeta(method);
175
304
  if (!meta) continue;
176
- const handler = /* @__PURE__ */ __name((input, log) => method.call(instance, input, log), "handler");
305
+ const boundMethod = method;
306
+ const handler = /* @__PURE__ */ __name(async (input, log) => {
307
+ const validInput = meta.input ? meta.input.parse(input) : input;
308
+ const output = await boundMethod.call(instance, validInput, log);
309
+ return meta.output ? meta.output.parse(output) : output;
310
+ }, "handler");
177
311
  register(meta, handler);
178
312
  }
179
313
  }
@@ -181,46 +315,54 @@ function scanSteps(discovery, scanner, register) {
181
315
  __name(scanSteps, "scanSteps");
182
316
 
183
317
  // src/durable-worker.module.ts
184
- function _ts_decorate(decorators, target, key, desc) {
318
+ function _ts_decorate2(decorators, target, key, desc) {
185
319
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
186
320
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
187
321
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
188
322
  return c > 3 && r && Object.defineProperty(target, key, r), r;
189
323
  }
190
- __name(_ts_decorate, "_ts_decorate");
191
- function _ts_metadata(k, v) {
324
+ __name(_ts_decorate2, "_ts_decorate");
325
+ function _ts_metadata2(k, v) {
192
326
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
193
327
  }
194
- __name(_ts_metadata, "_ts_metadata");
328
+ __name(_ts_metadata2, "_ts_metadata");
195
329
  function _ts_param(paramIndex, decorator) {
196
330
  return function(target, key) {
197
331
  decorator(target, key, paramIndex);
198
332
  };
199
333
  }
200
334
  __name(_ts_param, "_ts_param");
201
- var DURABLE_WORKER_OPTIONS = Symbol("nestjs-durable:worker-options");
202
335
  var RUN_REDIS_WORKER = Symbol("nestjs-durable:run-redis-worker");
203
336
  var DURABLE_WORKER_RUNNERS = Symbol("nestjs-durable:worker-runners");
337
+ function isPureThinWorker(options) {
338
+ return options.store === void 0 && options.connection !== void 0;
339
+ }
340
+ __name(isPureThinWorker, "isPureThinWorker");
204
341
  var ThinWorkflowRegistrar = class {
205
342
  static {
206
343
  __name(this, "ThinWorkflowRegistrar");
207
344
  }
208
345
  discovery;
209
346
  runtime;
210
- constructor(discovery, runtime) {
347
+ options;
348
+ constructor(discovery, runtime, options) {
211
349
  this.discovery = discovery;
212
350
  this.runtime = runtime;
351
+ this.options = options;
213
352
  }
214
353
  onModuleInit() {
354
+ if (!isPureThinWorker(this.options)) return;
215
355
  scanWorkflows(this.discovery, (meta, instance) => this.runtime.registerWorkflow(meta.name, (ctx, input) => instance.run(ctx, input)));
216
356
  }
217
357
  };
218
- ThinWorkflowRegistrar = _ts_decorate([
219
- (0, import_common.Injectable)(),
220
- _ts_metadata("design:type", Function),
221
- _ts_metadata("design:paramtypes", [
358
+ ThinWorkflowRegistrar = _ts_decorate2([
359
+ (0, import_common2.Injectable)(),
360
+ _ts_param(2, (0, import_common2.Inject)(import_nestjs_durable_core3.DURABLE_OPTIONS_CANONICAL)),
361
+ _ts_metadata2("design:type", Function),
362
+ _ts_metadata2("design:paramtypes", [
222
363
  typeof import_core.DiscoveryService === "undefined" ? Object : import_core.DiscoveryService,
223
- typeof import_durable_worker.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker.DurableWorkerRuntime
364
+ typeof import_durable_worker2.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker2.DurableWorkerRuntime,
365
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions
224
366
  ])
225
367
  ], ThinWorkflowRegistrar);
226
368
  var ThinStepRegistrar = class {
@@ -230,22 +372,27 @@ var ThinStepRegistrar = class {
230
372
  discovery;
231
373
  metadataScanner;
232
374
  runtime;
233
- constructor(discovery, metadataScanner, runtime) {
375
+ options;
376
+ constructor(discovery, metadataScanner, runtime, options) {
234
377
  this.discovery = discovery;
235
378
  this.metadataScanner = metadataScanner;
236
379
  this.runtime = runtime;
380
+ this.options = options;
237
381
  }
238
382
  onModuleInit() {
383
+ if (!isPureThinWorker(this.options)) return;
239
384
  scanSteps(this.discovery, this.metadataScanner, (meta, handler) => this.runtime.registerStep(meta.name, handler));
240
385
  }
241
386
  };
242
- ThinStepRegistrar = _ts_decorate([
243
- (0, import_common.Injectable)(),
244
- _ts_metadata("design:type", Function),
245
- _ts_metadata("design:paramtypes", [
387
+ ThinStepRegistrar = _ts_decorate2([
388
+ (0, import_common2.Injectable)(),
389
+ _ts_param(3, (0, import_common2.Inject)(import_nestjs_durable_core3.DURABLE_OPTIONS_CANONICAL)),
390
+ _ts_metadata2("design:type", Function),
391
+ _ts_metadata2("design:paramtypes", [
246
392
  typeof import_core.DiscoveryService === "undefined" ? Object : import_core.DiscoveryService,
247
393
  typeof import_core.MetadataScanner === "undefined" ? Object : import_core.MetadataScanner,
248
- typeof import_durable_worker.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker.DurableWorkerRuntime
394
+ typeof import_durable_worker2.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker2.DurableWorkerRuntime,
395
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions
249
396
  ])
250
397
  ], ThinStepRegistrar);
251
398
  var ThinWorkerBootstrap = class {
@@ -264,113 +411,139 @@ var ThinWorkerBootstrap = class {
264
411
  this.runnersSink = runnersSink;
265
412
  }
266
413
  async onApplicationBootstrap() {
267
- for (const group of this.options.groups) {
268
- const handle = await this.runRedisWorker({
269
- runtime: this.runtime,
270
- group,
271
- connection: this.options.connection,
272
- ...this.options.prefix !== void 0 ? {
273
- prefix: this.options.prefix
274
- } : {},
275
- ...this.options.instanceId !== void 0 ? {
276
- instanceId: this.options.instanceId
277
- } : {},
278
- ...(this.options.concurrencyByGroup?.[group] ?? this.options.concurrency) !== void 0 ? {
279
- concurrency: this.options.concurrencyByGroup?.[group] ?? this.options.concurrency
280
- } : {}
281
- });
282
- this.runners.push(handle);
283
- this.runnersSink.push(handle);
284
- }
414
+ const options = this.options;
415
+ if (!isPureThinWorker(options) || options.connection === void 0) return;
416
+ const handle = await this.runRedisWorker({
417
+ runtime: this.runtime,
418
+ connection: options.connection,
419
+ ...options.partition !== void 0 ? {
420
+ partition: options.partition
421
+ } : {},
422
+ ...options.prefix !== void 0 ? {
423
+ prefix: options.prefix
424
+ } : {},
425
+ ...options.instanceId !== void 0 ? {
426
+ instanceId: options.instanceId
427
+ } : {},
428
+ ...options.concurrency !== void 0 ? {
429
+ concurrency: options.concurrency
430
+ } : {}
431
+ });
432
+ this.runners.push(handle);
433
+ this.runnersSink.push(handle);
285
434
  }
286
435
  async onApplicationShutdown() {
287
436
  await Promise.allSettled(this.runners.map((h) => h.close()));
288
437
  }
289
438
  };
290
- ThinWorkerBootstrap = _ts_decorate([
291
- (0, import_common.Injectable)(),
292
- _ts_param(1, (0, import_common.Inject)(DURABLE_WORKER_OPTIONS)),
293
- _ts_param(2, (0, import_common.Inject)(RUN_REDIS_WORKER)),
294
- _ts_param(3, (0, import_common.Inject)(DURABLE_WORKER_RUNNERS)),
295
- _ts_metadata("design:type", Function),
296
- _ts_metadata("design:paramtypes", [
297
- typeof import_durable_worker.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker.DurableWorkerRuntime,
298
- typeof DurableWorkerModuleOptions === "undefined" ? Object : DurableWorkerModuleOptions,
439
+ ThinWorkerBootstrap = _ts_decorate2([
440
+ (0, import_common2.Injectable)(),
441
+ _ts_param(1, (0, import_common2.Inject)(import_nestjs_durable_core3.DURABLE_OPTIONS_CANONICAL)),
442
+ _ts_param(2, (0, import_common2.Inject)(RUN_REDIS_WORKER)),
443
+ _ts_param(3, (0, import_common2.Inject)(DURABLE_WORKER_RUNNERS)),
444
+ _ts_metadata2("design:type", Function),
445
+ _ts_metadata2("design:paramtypes", [
446
+ typeof import_durable_worker2.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker2.DurableWorkerRuntime,
447
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions,
299
448
  typeof RunRedisWorkerFn === "undefined" ? Object : RunRedisWorkerFn,
300
449
  Array
301
450
  ])
302
451
  ], ThinWorkerBootstrap);
303
- var DurableWorkerModule = class _DurableWorkerModule {
304
- static {
305
- __name(this, "DurableWorkerModule");
306
- }
307
- static forRoot(options) {
308
- return _DurableWorkerModule.build({
309
- provide: DURABLE_WORKER_OPTIONS,
310
- useValue: options
311
- });
312
- }
313
- static forRootAsync(options) {
314
- return _DurableWorkerModule.build({
315
- provide: DURABLE_WORKER_OPTIONS,
316
- useFactory: options.useFactory,
317
- inject: options.inject ?? []
318
- });
319
- }
320
- static build(optionsProvider) {
321
- return {
322
- module: _DurableWorkerModule,
323
- imports: [
324
- import_core.DiscoveryModule
325
- ],
326
- providers: [
327
- optionsProvider,
328
- {
329
- provide: import_durable_worker.DurableWorkerRuntime,
330
- useFactory: /* @__PURE__ */ __name(() => new import_durable_worker.DurableWorkerRuntime(), "useFactory")
331
- },
332
- {
333
- provide: RUN_REDIS_WORKER,
334
- useValue: import_durable_worker.runRedisWorker
335
- },
336
- {
337
- provide: DURABLE_WORKER_RUNNERS,
338
- useValue: []
339
- },
340
- ThinWorkflowRegistrar,
341
- ThinStepRegistrar,
342
- ThinWorkerBootstrap
343
- ],
344
- exports: [
345
- import_durable_worker.DurableWorkerRuntime
452
+ function thinWorkerProviders() {
453
+ return [
454
+ {
455
+ provide: import_durable_worker2.DurableWorkerRuntime,
456
+ // The runtime's `WorkflowWorker` falls back to its own `group` ctor param as the WORKFLOW's
457
+ // `workflowPartition` for any `ctx.step` call (see `workflow-context.ts`'s `resolveCallGroup`)
458
+ // — that fallback MUST equal this module's own `partition`, or a dispatched step's decision
459
+ // carries a mismatched token and the engine dispatches it to a queue nothing here subscribes
460
+ // to. Explicit `''` (never
461
+ // `undefined`) so it does NOT fall through to `WorkflowWorker`'s unrelated `'workflows'`
462
+ // default parameter.
463
+ useFactory: /* @__PURE__ */ __name((options) => new import_durable_worker2.DurableWorkerRuntime({
464
+ workflowGroup: options.partition ?? ""
465
+ }), "useFactory"),
466
+ inject: [
467
+ import_nestjs_durable_core3.DURABLE_OPTIONS_CANONICAL
346
468
  ]
347
- };
348
- }
349
- };
350
- DurableWorkerModule = _ts_decorate([
351
- (0, import_common.Module)({})
352
- ], DurableWorkerModule);
469
+ },
470
+ {
471
+ provide: RUN_REDIS_WORKER,
472
+ useValue: import_durable_worker2.runRedisWorker
473
+ },
474
+ {
475
+ provide: DURABLE_WORKER_RUNNERS,
476
+ useValue: []
477
+ },
478
+ ThinWorkflowRegistrar,
479
+ ThinStepRegistrar,
480
+ ThinWorkerBootstrap
481
+ ];
482
+ }
483
+ __name(thinWorkerProviders, "thinWorkerProviders");
484
+ function tenantGatewayUnavailable(method) {
485
+ return Promise.reject(new Error(`RunGateway.${method}() is not available \u2014 pass \`transport\` to use RunGateway.`));
486
+ }
487
+ __name(tenantGatewayUnavailable, "tenantGatewayUnavailable");
488
+ function unavailableRunGateway() {
489
+ return {
490
+ getRunDetail(_runId) {
491
+ return tenantGatewayUnavailable("getRunDetail");
492
+ },
493
+ listRuns(_query) {
494
+ return tenantGatewayUnavailable("listRuns");
495
+ },
496
+ cancel(_runId) {
497
+ return tenantGatewayUnavailable("cancel");
498
+ },
499
+ retry(_runId) {
500
+ return tenantGatewayUnavailable("retry");
501
+ },
502
+ continue(_runId) {
503
+ return tenantGatewayUnavailable("continue");
504
+ },
505
+ retryWithInput(_runId, _input) {
506
+ return tenantGatewayUnavailable("retryWithInput");
507
+ },
508
+ subscribe(_runId, _onEvent) {
509
+ throw new Error("RunGateway.subscribe() is not available \u2014 pass `transport` to use RunGateway.");
510
+ }
511
+ };
512
+ }
513
+ __name(unavailableRunGateway, "unavailableRunGateway");
353
514
 
354
515
  // src/durable.module.ts
355
- var import_nestjs_durable_core9 = require("@dudousxd/nestjs-durable-core");
356
- var import_common9 = require("@nestjs/common");
516
+ var import_nestjs_durable_core12 = require("@dudousxd/nestjs-durable-core");
517
+ var import_common12 = require("@nestjs/common");
357
518
  var import_core5 = require("@nestjs/core");
358
519
 
359
520
  // src/durable-step.registrar.ts
360
- var import_nestjs_durable_core2 = require("@dudousxd/nestjs-durable-core");
361
- var import_common2 = require("@nestjs/common");
521
+ var import_nestjs_durable_core4 = require("@dudousxd/nestjs-durable-core");
522
+ var import_common3 = require("@nestjs/common");
362
523
  var import_core2 = require("@nestjs/core");
363
- function _ts_decorate2(decorators, target, key, desc) {
524
+
525
+ // src/role.ts
526
+ function isOperatorRole(options) {
527
+ return options.store !== void 0;
528
+ }
529
+ __name(isOperatorRole, "isOperatorRole");
530
+ function isDrivingOperator(options) {
531
+ return isOperatorRole(options) && options.drive !== false;
532
+ }
533
+ __name(isDrivingOperator, "isDrivingOperator");
534
+
535
+ // src/durable-step.registrar.ts
536
+ function _ts_decorate3(decorators, target, key, desc) {
364
537
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
365
538
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
366
539
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
367
540
  return c > 3 && r && Object.defineProperty(target, key, r), r;
368
541
  }
369
- __name(_ts_decorate2, "_ts_decorate");
370
- function _ts_metadata2(k, v) {
542
+ __name(_ts_decorate3, "_ts_decorate");
543
+ function _ts_metadata3(k, v) {
371
544
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
372
545
  }
373
- __name(_ts_metadata2, "_ts_metadata");
546
+ __name(_ts_metadata3, "_ts_metadata");
374
547
  function _ts_param2(paramIndex, decorator) {
375
548
  return function(target, key) {
376
549
  decorator(target, key, paramIndex);
@@ -396,18 +569,18 @@ var DurableStepRegistrar = class {
396
569
  this.options = options;
397
570
  }
398
571
  onModuleInit() {
399
- if (this.options.worker === false) return;
572
+ if (!isDrivingOperator(this.options)) return;
400
573
  if (!supportsHandle(this.transport)) return;
401
574
  const transport = this.transport;
402
575
  scanSteps(this.discovery, this.metadataScanner, (meta, handler) => transport.handle(meta.name, handler));
403
576
  }
404
577
  };
405
- DurableStepRegistrar = _ts_decorate2([
406
- (0, import_common2.Injectable)(),
407
- _ts_param2(2, (0, import_common2.Inject)(import_nestjs_durable_core2.TRANSPORT_CANONICAL)),
408
- _ts_param2(3, (0, import_common2.Inject)(import_nestjs_durable_core2.DURABLE_OPTIONS_CANONICAL)),
409
- _ts_metadata2("design:type", Function),
410
- _ts_metadata2("design:paramtypes", [
578
+ DurableStepRegistrar = _ts_decorate3([
579
+ (0, import_common3.Injectable)(),
580
+ _ts_param2(2, (0, import_common3.Inject)(import_nestjs_durable_core4.TRANSPORT_CANONICAL)),
581
+ _ts_param2(3, (0, import_common3.Inject)(import_nestjs_durable_core4.DURABLE_OPTIONS_CANONICAL)),
582
+ _ts_metadata3("design:type", Function),
583
+ _ts_metadata3("design:paramtypes", [
411
584
  typeof import_core2.DiscoveryService === "undefined" ? Object : import_core2.DiscoveryService,
412
585
  typeof import_core2.MetadataScanner === "undefined" ? Object : import_core2.MetadataScanner,
413
586
  Object,
@@ -416,20 +589,20 @@ DurableStepRegistrar = _ts_decorate2([
416
589
  ], DurableStepRegistrar);
417
590
 
418
591
  // src/entity.ts
419
- var import_nestjs_durable_core3 = require("@dudousxd/nestjs-durable-core");
420
- var import_common3 = require("@nestjs/common");
592
+ var import_nestjs_durable_core5 = require("@dudousxd/nestjs-durable-core");
593
+ var import_common4 = require("@nestjs/common");
421
594
  var import_reflect_metadata2 = require("reflect-metadata");
422
- function _ts_decorate3(decorators, target, key, desc) {
595
+ function _ts_decorate4(decorators, target, key, desc) {
423
596
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
424
597
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
425
598
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
426
599
  return c > 3 && r && Object.defineProperty(target, key, r), r;
427
600
  }
428
- __name(_ts_decorate3, "_ts_decorate");
429
- function _ts_metadata3(k, v) {
601
+ __name(_ts_decorate4, "_ts_decorate");
602
+ function _ts_metadata4(k, v) {
430
603
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
431
604
  }
432
- __name(_ts_metadata3, "_ts_metadata");
605
+ __name(_ts_metadata4, "_ts_metadata");
433
606
  var ENTITY_METADATA = Symbol("nestjs-durable:entity");
434
607
  var ENTITY_ON_METADATA = Symbol("nestjs-durable:entity-on");
435
608
  function Entity(options) {
@@ -486,49 +659,54 @@ var EntityService = class {
486
659
  return this.engine.getEntityState(name, key);
487
660
  }
488
661
  };
489
- EntityService = _ts_decorate3([
490
- (0, import_common3.Injectable)(),
491
- _ts_metadata3("design:type", Function),
492
- _ts_metadata3("design:paramtypes", [
493
- typeof import_nestjs_durable_core3.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core3.WorkflowEngine
662
+ EntityService = _ts_decorate4([
663
+ (0, import_common4.Injectable)(),
664
+ _ts_metadata4("design:type", Function),
665
+ _ts_metadata4("design:paramtypes", [
666
+ typeof import_nestjs_durable_core5.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core5.WorkflowEngine
494
667
  ])
495
668
  ], EntityService);
496
669
 
497
670
  // src/in-app-worker.ts
498
- var import_durable_worker2 = require("@dudousxd/durable-worker");
499
- var import_nestjs_durable_core4 = require("@dudousxd/nestjs-durable-core");
500
- var import_common4 = require("@nestjs/common");
671
+ var import_durable_worker3 = require("@dudousxd/durable-worker");
672
+ var import_nestjs_durable_core6 = require("@dudousxd/nestjs-durable-core");
673
+ var import_common5 = require("@nestjs/common");
501
674
  var import_core3 = require("@nestjs/core");
502
- function _ts_decorate4(decorators, target, key, desc) {
675
+ function _ts_decorate5(decorators, target, key, desc) {
503
676
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
504
677
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
505
678
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
506
679
  return c > 3 && r && Object.defineProperty(target, key, r), r;
507
680
  }
508
- __name(_ts_decorate4, "_ts_decorate");
509
- function _ts_metadata4(k, v) {
681
+ __name(_ts_decorate5, "_ts_decorate");
682
+ function _ts_metadata5(k, v) {
510
683
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
511
684
  }
512
- __name(_ts_metadata4, "_ts_metadata");
685
+ __name(_ts_metadata5, "_ts_metadata");
513
686
  function _ts_param3(paramIndex, decorator) {
514
687
  return function(target, key) {
515
688
  decorator(target, key, paramIndex);
516
689
  };
517
690
  }
518
691
  __name(_ts_param3, "_ts_param");
519
- var IN_APP_WORKER_OPTIONS = Symbol("nestjs-durable:in-app-worker-options");
520
692
  var IN_APP_WORKER_BINDING = Symbol("nestjs-durable:in-app-worker-binding");
521
693
  var IN_APP_WORKER_RUNTIME = Symbol("nestjs-durable:in-app-worker-runtime");
522
694
  var IN_APP_RUN_REDIS_WORKER = Symbol("nestjs-durable:in-app-run-redis-worker");
523
695
  var IN_APP_WORKER_RUNNERS = Symbol("nestjs-durable:in-app-worker-runners");
696
+ function isCoLocatedWorker(options) {
697
+ return options.store !== void 0 && options.connection !== void 0;
698
+ }
699
+ __name(isCoLocatedWorker, "isCoLocatedWorker");
524
700
  function inAppWorkerBinding(transport, options) {
525
- if (!options) return null;
701
+ if (!isCoLocatedWorker(options)) return null;
526
702
  if (!transport?.dispatchWorkflowTask || !transport.onDecision) {
527
- throw new Error("inAppWorker requires a transport that carries workflow tasks (dispatchWorkflowTask + onDecision), e.g. BullMQTransport. An in-process transport cannot serve a group-served workflow.");
703
+ throw new Error("a co-located worker (store + connection) requires a transport that carries workflow tasks (dispatchWorkflowTask + onDecision), e.g. BullMQTransport. An in-process transport cannot serve a group-served workflow.");
528
704
  }
529
705
  return {
530
- group: options.group,
531
- executor: new import_nestjs_durable_core4.RemoteWorkflowExecutor(transport, options.group)
706
+ transport,
707
+ ...options.partition !== void 0 ? {
708
+ partition: options.partition
709
+ } : {}
532
710
  };
533
711
  }
534
712
  __name(inAppWorkerBinding, "inAppWorkerBinding");
@@ -552,24 +730,27 @@ var InAppWorkerBootstrap = class {
552
730
  this.runnersSink = runnersSink;
553
731
  }
554
732
  onModuleInit() {
555
- if (!this.options) return;
733
+ if (!isCoLocatedWorker(this.options)) return;
556
734
  scanWorkflows(this.discovery, (meta, instance) => this.runtime.registerWorkflow(meta.name, (ctx, input) => instance.run(ctx, input)));
557
735
  scanSteps(this.discovery, this.metadataScanner, (meta, handler) => this.runtime.registerStep(meta.name, handler));
558
736
  }
559
737
  async onApplicationBootstrap() {
560
- if (!this.options) return;
738
+ const options = this.options;
739
+ if (!isCoLocatedWorker(options) || options.connection === void 0) return;
561
740
  const handle = await this.runRedisWorker({
562
741
  runtime: this.runtime,
563
- group: this.options.group,
564
- connection: this.options.connection,
565
- ...this.options.prefix !== void 0 ? {
566
- prefix: this.options.prefix
742
+ connection: options.connection,
743
+ ...options.partition !== void 0 ? {
744
+ partition: options.partition
745
+ } : {},
746
+ ...options.prefix !== void 0 ? {
747
+ prefix: options.prefix
567
748
  } : {},
568
- ...this.options.instanceId !== void 0 ? {
569
- instanceId: this.options.instanceId
749
+ ...options.instanceId !== void 0 ? {
750
+ instanceId: options.instanceId
570
751
  } : {},
571
- ...this.options.concurrency !== void 0 ? {
572
- concurrency: this.options.concurrency
752
+ ...options.concurrency !== void 0 ? {
753
+ concurrency: options.concurrency
573
754
  } : {}
574
755
  });
575
756
  this.runners.push(handle);
@@ -579,18 +760,18 @@ var InAppWorkerBootstrap = class {
579
760
  await Promise.allSettled(this.runners.map((handle) => handle.close()));
580
761
  }
581
762
  };
582
- InAppWorkerBootstrap = _ts_decorate4([
583
- (0, import_common4.Injectable)(),
584
- _ts_param3(2, (0, import_common4.Inject)(IN_APP_WORKER_OPTIONS)),
585
- _ts_param3(3, (0, import_common4.Inject)(IN_APP_WORKER_RUNTIME)),
586
- _ts_param3(4, (0, import_common4.Inject)(IN_APP_RUN_REDIS_WORKER)),
587
- _ts_param3(5, (0, import_common4.Inject)(IN_APP_WORKER_RUNNERS)),
588
- _ts_metadata4("design:type", Function),
589
- _ts_metadata4("design:paramtypes", [
763
+ InAppWorkerBootstrap = _ts_decorate5([
764
+ (0, import_common5.Injectable)(),
765
+ _ts_param3(2, (0, import_common5.Inject)(import_nestjs_durable_core6.DURABLE_OPTIONS_CANONICAL)),
766
+ _ts_param3(3, (0, import_common5.Inject)(IN_APP_WORKER_RUNTIME)),
767
+ _ts_param3(4, (0, import_common5.Inject)(IN_APP_RUN_REDIS_WORKER)),
768
+ _ts_param3(5, (0, import_common5.Inject)(IN_APP_WORKER_RUNNERS)),
769
+ _ts_metadata5("design:type", Function),
770
+ _ts_metadata5("design:paramtypes", [
590
771
  typeof import_core3.DiscoveryService === "undefined" ? Object : import_core3.DiscoveryService,
591
772
  typeof import_core3.MetadataScanner === "undefined" ? Object : import_core3.MetadataScanner,
592
- Object,
593
- typeof import_durable_worker2.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker2.DurableWorkerRuntime,
773
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions,
774
+ typeof import_durable_worker3.DurableWorkerRuntime === "undefined" ? Object : import_durable_worker3.DurableWorkerRuntime,
594
775
  typeof RunRedisWorkerFn === "undefined" ? Object : RunRedisWorkerFn,
595
776
  Array
596
777
  ])
@@ -599,26 +780,31 @@ function inAppWorkerProviders() {
599
780
  return [
600
781
  {
601
782
  provide: IN_APP_WORKER_BINDING,
602
- useFactory: /* @__PURE__ */ __name((transport, options) => inAppWorkerBinding(transport, options.inAppWorker ?? null), "useFactory"),
783
+ useFactory: /* @__PURE__ */ __name((transport, options) => inAppWorkerBinding(transport, options), "useFactory"),
603
784
  inject: [
604
- import_nestjs_durable_core4.TRANSPORT_CANONICAL,
605
- import_nestjs_durable_core4.DURABLE_OPTIONS_CANONICAL
785
+ import_nestjs_durable_core6.TRANSPORT_CANONICAL,
786
+ import_nestjs_durable_core6.DURABLE_OPTIONS_CANONICAL
606
787
  ]
607
788
  },
608
789
  {
609
- provide: IN_APP_WORKER_OPTIONS,
610
- useFactory: /* @__PURE__ */ __name((options) => options.inAppWorker ?? null, "useFactory"),
790
+ provide: IN_APP_WORKER_RUNTIME,
791
+ // The runtime's `WorkflowWorker` uses its `group` ctor param as the WORKFLOW's
792
+ // `workflowPartition` for any `ctx.step` call (see `workflow-context.ts`'s `resolveCallGroup`)
793
+ // — that fallback MUST equal this app's own `partition`, or a dispatched step's decision
794
+ // carries a mismatched token and the engine dispatches it to a queue nothing here subscribes
795
+ // to. Explicit `''` (never
796
+ // `undefined`) so it does NOT fall through to `WorkflowWorker`'s unrelated `'workflows'`
797
+ // default parameter.
798
+ useFactory: /* @__PURE__ */ __name((options) => new import_durable_worker3.DurableWorkerRuntime({
799
+ workflowGroup: options.partition ?? ""
800
+ }), "useFactory"),
611
801
  inject: [
612
- import_nestjs_durable_core4.DURABLE_OPTIONS_CANONICAL
802
+ import_nestjs_durable_core6.DURABLE_OPTIONS_CANONICAL
613
803
  ]
614
804
  },
615
- {
616
- provide: IN_APP_WORKER_RUNTIME,
617
- useFactory: /* @__PURE__ */ __name(() => new import_durable_worker2.DurableWorkerRuntime(), "useFactory")
618
- },
619
805
  {
620
806
  provide: IN_APP_RUN_REDIS_WORKER,
621
- useValue: import_durable_worker2.runRedisWorker
807
+ useValue: import_durable_worker3.runRedisWorker
622
808
  },
623
809
  {
624
810
  provide: IN_APP_WORKER_RUNNERS,
@@ -629,20 +815,142 @@ function inAppWorkerProviders() {
629
815
  }
630
816
  __name(inAppWorkerProviders, "inAppWorkerProviders");
631
817
 
818
+ // src/proxy-run-gateway.ts
819
+ var import_common6 = require("@nestjs/common");
820
+ function _ts_decorate6(decorators, target, key, desc) {
821
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
822
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
823
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
824
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
825
+ }
826
+ __name(_ts_decorate6, "_ts_decorate");
827
+ function _ts_metadata6(k, v) {
828
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
829
+ }
830
+ __name(_ts_metadata6, "_ts_metadata");
831
+ var ProxyRunGateway = class {
832
+ static {
833
+ __name(this, "ProxyRunGateway");
834
+ }
835
+ transport;
836
+ tenant;
837
+ timeoutMs;
838
+ pending = /* @__PURE__ */ new Map();
839
+ constructor(transport, tenant, timeoutMs = 1e4) {
840
+ this.transport = transport;
841
+ this.tenant = tenant;
842
+ this.timeoutMs = timeoutMs;
843
+ this.transport.onRunReply?.((reply) => this.handleReply(reply));
844
+ }
845
+ handleReply(reply) {
846
+ const pending = this.pending.get(reply.requestId);
847
+ if (!pending) return;
848
+ clearTimeout(pending.timer);
849
+ this.pending.delete(reply.requestId);
850
+ if (reply.result.ok) {
851
+ pending.resolve(reply.result.data);
852
+ } else {
853
+ pending.reject(new Error(reply.result.error.message));
854
+ }
855
+ }
856
+ request(body) {
857
+ return new Promise((resolve, reject) => {
858
+ const requestId = globalThis.crypto.randomUUID();
859
+ const timer = setTimeout(() => {
860
+ this.pending.delete(requestId);
861
+ reject(new Error(`control plane did not respond to ${body.kind} within ${this.timeoutMs}ms`));
862
+ }, this.timeoutMs);
863
+ this.pending.set(requestId, {
864
+ resolve,
865
+ reject,
866
+ timer
867
+ });
868
+ this.transport.dispatchRunRequest?.({
869
+ requestId,
870
+ tenant: this.tenant,
871
+ body
872
+ }).catch((error) => {
873
+ const stillPending = this.pending.get(requestId);
874
+ if (!stillPending) return;
875
+ clearTimeout(stillPending.timer);
876
+ this.pending.delete(requestId);
877
+ stillPending.reject(error instanceof Error ? error : new Error(String(error)));
878
+ });
879
+ });
880
+ }
881
+ getRunDetail(runId) {
882
+ return this.request({
883
+ kind: "getRunDetail",
884
+ runId
885
+ });
886
+ }
887
+ listRuns(query) {
888
+ return this.request({
889
+ kind: "listRuns",
890
+ query
891
+ });
892
+ }
893
+ cancel(runId, opts) {
894
+ return this.request(opts === void 0 ? {
895
+ kind: "cancel",
896
+ runId
897
+ } : {
898
+ kind: "cancel",
899
+ runId,
900
+ opts
901
+ });
902
+ }
903
+ retry(runId) {
904
+ return this.request({
905
+ kind: "retry",
906
+ runId
907
+ });
908
+ }
909
+ continue(runId) {
910
+ return this.request({
911
+ kind: "continue",
912
+ runId
913
+ });
914
+ }
915
+ retryWithInput(runId, input) {
916
+ return this.request({
917
+ kind: "retryWithInput",
918
+ runId,
919
+ input
920
+ });
921
+ }
922
+ subscribe(runId, onEvent) {
923
+ const unsubscribe = this.transport.onTenantEvent?.(this.tenant, (evt) => {
924
+ if (evt.event.runId === runId) onEvent(evt.event);
925
+ });
926
+ return unsubscribe ?? (() => {
927
+ });
928
+ }
929
+ };
930
+ ProxyRunGateway = _ts_decorate6([
931
+ (0, import_common6.Injectable)(),
932
+ _ts_metadata6("design:type", Function),
933
+ _ts_metadata6("design:paramtypes", [
934
+ typeof Transport === "undefined" ? Object : Transport,
935
+ String,
936
+ void 0
937
+ ])
938
+ ], ProxyRunGateway);
939
+
632
940
  // src/retention-poller.ts
633
- var import_nestjs_durable_core5 = require("@dudousxd/nestjs-durable-core");
634
- var import_common5 = require("@nestjs/common");
635
- function _ts_decorate5(decorators, target, key, desc) {
941
+ var import_nestjs_durable_core7 = require("@dudousxd/nestjs-durable-core");
942
+ var import_common7 = require("@nestjs/common");
943
+ function _ts_decorate7(decorators, target, key, desc) {
636
944
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
637
945
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
638
946
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
639
947
  return c > 3 && r && Object.defineProperty(target, key, r), r;
640
948
  }
641
- __name(_ts_decorate5, "_ts_decorate");
642
- function _ts_metadata5(k, v) {
949
+ __name(_ts_decorate7, "_ts_decorate");
950
+ function _ts_metadata7(k, v) {
643
951
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
644
952
  }
645
- __name(_ts_metadata5, "_ts_metadata");
953
+ __name(_ts_metadata7, "_ts_metadata");
646
954
  function _ts_param4(paramIndex, decorator) {
647
955
  return function(target, key) {
648
956
  decorator(target, key, paramIndex);
@@ -661,10 +969,10 @@ function validateRetention(retention) {
661
969
  if (policy.maxAge == null && policy.maxCount == null) {
662
970
  throw new Error("durable retention: each policy must set maxAge and/or maxCount");
663
971
  }
664
- if (policy.maxAge != null) (0, import_nestjs_durable_core5.parseDuration)(policy.maxAge);
972
+ if (policy.maxAge != null) (0, import_nestjs_durable_core7.parseDuration)(policy.maxAge);
665
973
  for (const status of policy.statuses) {
666
- if (!import_nestjs_durable_core5.TERMINAL_RUN_STATUSES.includes(status)) {
667
- throw new Error(`durable retention: status "${status}" is not terminal; only ${import_nestjs_durable_core5.TERMINAL_RUN_STATUSES.join(", ")} can be pruned`);
974
+ if (!import_nestjs_durable_core7.TERMINAL_RUN_STATUSES.includes(status)) {
975
+ throw new Error(`durable retention: status "${status}" is not terminal; only ${import_nestjs_durable_core7.TERMINAL_RUN_STATUSES.join(", ")} can be pruned`);
668
976
  }
669
977
  if (seen.has(status)) {
670
978
  throw new Error(`durable retention: status "${status}" appears in more than one policy; status sets must be disjoint`);
@@ -686,17 +994,24 @@ var RetentionPoller = class {
686
994
  this.store = store;
687
995
  this.options = options;
688
996
  }
997
+ /** Non-null once past the `isDrivingOperator` guard (which requires `options.store` to be set). */
998
+ requireStore() {
999
+ if (!this.store) {
1000
+ throw new Error("unreachable: STATE_STORE_CANONICAL must resolve a store when options.store is set");
1001
+ }
1002
+ return this.store;
1003
+ }
689
1004
  async onApplicationBootstrap() {
690
- if (this.options.worker === false) return;
1005
+ if (!isDrivingOperator(this.options)) return;
691
1006
  const retention = this.options.retention;
692
1007
  if (!retention || retention.policies.length === 0) return;
693
1008
  validateRetention(retention);
694
- if (typeof this.store.pruneTerminalRuns !== "function") {
1009
+ if (typeof this.requireStore().pruneTerminalRuns !== "function") {
695
1010
  console.warn("[nestjs-durable] `retention` is configured but the store adapter does not implement pruneTerminalRuns; retention is disabled.");
696
1011
  return;
697
1012
  }
698
1013
  await this.sweep();
699
- const intervalMs = retention.sweepInterval != null ? (0, import_nestjs_durable_core5.parseDuration)(retention.sweepInterval) : DEFAULT_SWEEP_INTERVAL_MS;
1014
+ const intervalMs = retention.sweepInterval != null ? (0, import_nestjs_durable_core7.parseDuration)(retention.sweepInterval) : DEFAULT_SWEEP_INTERVAL_MS;
700
1015
  if (intervalMs > 0) {
701
1016
  this.timer = setInterval(() => void this.sweep(), intervalMs);
702
1017
  this.timer.unref?.();
@@ -708,7 +1023,8 @@ var RetentionPoller = class {
708
1023
  async sweep() {
709
1024
  if (this.sweeping) return;
710
1025
  const retention = this.options.retention;
711
- const prune = this.store.pruneTerminalRuns;
1026
+ const store = this.requireStore();
1027
+ const prune = store.pruneTerminalRuns;
712
1028
  if (!retention || typeof prune !== "function") return;
713
1029
  this.sweeping = true;
714
1030
  try {
@@ -716,7 +1032,7 @@ var RetentionPoller = class {
716
1032
  const now = Date.now();
717
1033
  for (const policy of retention.policies) {
718
1034
  for (let batch = 0; batch < MAX_BATCHES_PER_POLICY; batch++) {
719
- const deleted = await prune.call(this.store, policy, now, batchSize);
1035
+ const deleted = await prune.call(store, policy, now, batchSize);
720
1036
  if (deleted < batchSize) break;
721
1037
  }
722
1038
  }
@@ -725,37 +1041,244 @@ var RetentionPoller = class {
725
1041
  }
726
1042
  }
727
1043
  };
728
- RetentionPoller = _ts_decorate5([
729
- (0, import_common5.Injectable)(),
730
- _ts_param4(0, (0, import_common5.Inject)(import_nestjs_durable_core5.STATE_STORE_CANONICAL)),
731
- _ts_param4(1, (0, import_common5.Inject)(import_nestjs_durable_core5.DURABLE_OPTIONS_CANONICAL)),
732
- _ts_metadata5("design:type", Function),
733
- _ts_metadata5("design:paramtypes", [
734
- typeof StateStore === "undefined" ? Object : StateStore,
1044
+ RetentionPoller = _ts_decorate7([
1045
+ (0, import_common7.Injectable)(),
1046
+ _ts_param4(0, (0, import_common7.Inject)(import_nestjs_durable_core7.STATE_STORE_CANONICAL)),
1047
+ _ts_param4(1, (0, import_common7.Inject)(import_nestjs_durable_core7.DURABLE_OPTIONS_CANONICAL)),
1048
+ _ts_metadata7("design:type", Function),
1049
+ _ts_metadata7("design:paramtypes", [
1050
+ Object,
735
1051
  typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions
736
1052
  ])
737
1053
  ], RetentionPoller);
738
1054
 
739
- // src/timer-poller.ts
740
- var import_nestjs_durable_core6 = require("@dudousxd/nestjs-durable-core");
741
- var import_common6 = require("@nestjs/common");
742
- function _ts_decorate6(decorators, target, key, desc) {
1055
+ // src/run-request-responder.ts
1056
+ var RunRequestResponder = class {
1057
+ static {
1058
+ __name(this, "RunRequestResponder");
1059
+ }
1060
+ transport;
1061
+ gateway;
1062
+ constructor(transport, gateway) {
1063
+ this.transport = transport;
1064
+ this.gateway = gateway;
1065
+ }
1066
+ /** Register the consumer on the transport. Each request is answered independently; a handler
1067
+ * failure never throws back into the transport (errors are captured into an error reply). */
1068
+ start() {
1069
+ this.transport.onRunRequest(async (msg) => {
1070
+ const reply = await this.handle(msg);
1071
+ await this.transport.publishRunReply(reply);
1072
+ });
1073
+ }
1074
+ async handle(msg) {
1075
+ const { body } = msg;
1076
+ if (body.kind === "listRuns") {
1077
+ const data = await this.gateway.listRuns({
1078
+ ...body.query,
1079
+ namespace: msg.tenant
1080
+ });
1081
+ return {
1082
+ requestId: msg.requestId,
1083
+ result: {
1084
+ ok: true,
1085
+ data
1086
+ }
1087
+ };
1088
+ }
1089
+ const detail = await this.gateway.getRunDetail(body.runId);
1090
+ if (detail && detail.run.namespace !== msg.tenant) {
1091
+ return {
1092
+ requestId: msg.requestId,
1093
+ result: {
1094
+ ok: false,
1095
+ error: {
1096
+ message: "run belongs to another tenant",
1097
+ code: "cross-tenant"
1098
+ }
1099
+ }
1100
+ };
1101
+ }
1102
+ if (body.kind === "getRunDetail") {
1103
+ return {
1104
+ requestId: msg.requestId,
1105
+ result: {
1106
+ ok: true,
1107
+ data: detail
1108
+ }
1109
+ };
1110
+ }
1111
+ try {
1112
+ const data = await this.callVerb(body);
1113
+ return {
1114
+ requestId: msg.requestId,
1115
+ result: {
1116
+ ok: true,
1117
+ data
1118
+ }
1119
+ };
1120
+ } catch (err) {
1121
+ return {
1122
+ requestId: msg.requestId,
1123
+ result: {
1124
+ ok: false,
1125
+ error: {
1126
+ message: err instanceof Error ? err.message : String(err)
1127
+ }
1128
+ }
1129
+ };
1130
+ }
1131
+ }
1132
+ callVerb(body) {
1133
+ switch (body.kind) {
1134
+ case "cancel":
1135
+ return this.gateway.cancel(body.runId, body.opts);
1136
+ case "retry":
1137
+ return this.gateway.retry(body.runId);
1138
+ case "continue":
1139
+ return this.gateway.continue(body.runId);
1140
+ case "retryWithInput":
1141
+ return this.gateway.retryWithInput(body.runId, body.input);
1142
+ }
1143
+ }
1144
+ };
1145
+
1146
+ // src/store-run-gateway.ts
1147
+ var import_nestjs_durable_core8 = require("@dudousxd/nestjs-durable-core");
1148
+ var import_common8 = require("@nestjs/common");
1149
+ function _ts_decorate8(decorators, target, key, desc) {
743
1150
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
744
1151
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
745
1152
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
746
1153
  return c > 3 && r && Object.defineProperty(target, key, r), r;
747
1154
  }
748
- __name(_ts_decorate6, "_ts_decorate");
749
- function _ts_metadata6(k, v) {
1155
+ __name(_ts_decorate8, "_ts_decorate");
1156
+ function _ts_metadata8(k, v) {
750
1157
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
751
1158
  }
752
- __name(_ts_metadata6, "_ts_metadata");
1159
+ __name(_ts_metadata8, "_ts_metadata");
753
1160
  function _ts_param5(paramIndex, decorator) {
754
1161
  return function(target, key) {
755
1162
  decorator(target, key, paramIndex);
756
1163
  };
757
1164
  }
758
1165
  __name(_ts_param5, "_ts_param");
1166
+ var StoreRunGateway = class {
1167
+ static {
1168
+ __name(this, "StoreRunGateway");
1169
+ }
1170
+ store;
1171
+ engine;
1172
+ constructor(store, engine) {
1173
+ this.store = store;
1174
+ this.engine = engine;
1175
+ }
1176
+ async getRunDetail(runId) {
1177
+ const run = await this.store.getRun(runId);
1178
+ if (!run) return null;
1179
+ const [timeline, children] = await Promise.all([
1180
+ this.store.listCheckpoints(runId),
1181
+ this.engine.getRunChildren(runId)
1182
+ ]);
1183
+ return {
1184
+ run,
1185
+ timeline,
1186
+ children
1187
+ };
1188
+ }
1189
+ listRuns(query) {
1190
+ return this.store.listRuns(query);
1191
+ }
1192
+ cancel(runId, opts) {
1193
+ return this.engine.cancel(runId, opts);
1194
+ }
1195
+ /** Re-enqueue (dispatch model) instead of resuming inline — a worker picks the run up and replays it. */
1196
+ retry(runId) {
1197
+ return this.engine.requeue(runId);
1198
+ }
1199
+ continue(runId) {
1200
+ return this.engine.continue(runId);
1201
+ }
1202
+ retryWithInput(runId, input) {
1203
+ return this.engine.retryWithInput(runId, input);
1204
+ }
1205
+ subscribe(runId, onEvent) {
1206
+ return this.engine.subscribe((event) => {
1207
+ if (event.runId === runId) onEvent(event);
1208
+ });
1209
+ }
1210
+ };
1211
+ StoreRunGateway = _ts_decorate8([
1212
+ (0, import_common8.Injectable)(),
1213
+ _ts_param5(0, (0, import_common8.Inject)(import_nestjs_durable_core8.STATE_STORE_CANONICAL)),
1214
+ _ts_metadata8("design:type", Function),
1215
+ _ts_metadata8("design:paramtypes", [
1216
+ typeof StateStore === "undefined" ? Object : StateStore,
1217
+ typeof import_nestjs_durable_core8.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core8.WorkflowEngine
1218
+ ])
1219
+ ], StoreRunGateway);
1220
+
1221
+ // src/tenant-event-republisher.ts
1222
+ function isTerminalRunEvent(event) {
1223
+ return event.type === "run.completed" || event.type === "run.failed";
1224
+ }
1225
+ __name(isTerminalRunEvent, "isTerminalRunEvent");
1226
+ var TenantEventRepublisher = class {
1227
+ static {
1228
+ __name(this, "TenantEventRepublisher");
1229
+ }
1230
+ store;
1231
+ publish;
1232
+ runNamespaces = /* @__PURE__ */ new Map();
1233
+ constructor(store, publish) {
1234
+ this.store = store;
1235
+ this.publish = publish;
1236
+ }
1237
+ async handle(event) {
1238
+ const namespace = await this.namespaceFor(event);
1239
+ if (isTerminalRunEvent(event)) this.runNamespaces.delete(event.runId);
1240
+ if (!namespace || namespace === "default") return;
1241
+ await this.publish({
1242
+ tenant: namespace,
1243
+ event
1244
+ }).catch(() => void 0);
1245
+ }
1246
+ async namespaceFor(event) {
1247
+ if (this.runNamespaces.has(event.runId)) {
1248
+ const cached = this.runNamespaces.get(event.runId);
1249
+ return cached === null ? void 0 : cached;
1250
+ }
1251
+ if (event.namespace !== void 0) {
1252
+ this.runNamespaces.set(event.runId, event.namespace === "default" ? null : event.namespace);
1253
+ return event.namespace;
1254
+ }
1255
+ const run = await this.store.getRun(event.runId);
1256
+ const tenantNamespace = run?.namespace !== void 0 && run.namespace !== "default" ? run.namespace : null;
1257
+ this.runNamespaces.set(event.runId, tenantNamespace);
1258
+ return tenantNamespace === null ? void 0 : tenantNamespace;
1259
+ }
1260
+ };
1261
+
1262
+ // src/timer-poller.ts
1263
+ var import_nestjs_durable_core9 = require("@dudousxd/nestjs-durable-core");
1264
+ var import_common9 = require("@nestjs/common");
1265
+ function _ts_decorate9(decorators, target, key, desc) {
1266
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1267
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1268
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1269
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1270
+ }
1271
+ __name(_ts_decorate9, "_ts_decorate");
1272
+ function _ts_metadata9(k, v) {
1273
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1274
+ }
1275
+ __name(_ts_metadata9, "_ts_metadata");
1276
+ function _ts_param6(paramIndex, decorator) {
1277
+ return function(target, key) {
1278
+ decorator(target, key, paramIndex);
1279
+ };
1280
+ }
1281
+ __name(_ts_param6, "_ts_param");
759
1282
  var TimerPoller = class {
760
1283
  static {
761
1284
  __name(this, "TimerPoller");
@@ -770,7 +1293,7 @@ var TimerPoller = class {
770
1293
  this.options = options;
771
1294
  }
772
1295
  async onApplicationBootstrap() {
773
- if (this.options.worker === false) return;
1296
+ if (!isDrivingOperator(this.options)) return;
774
1297
  this.unsubscribeEnqueued = this.engine.onEnqueued((runId) => void this.engine.runOne(runId));
775
1298
  await this.poll();
776
1299
  const intervalMs = this.options.timerPollMs ?? 1e3;
@@ -793,29 +1316,30 @@ var TimerPoller = class {
793
1316
  await this.engine.sweepTimeouts();
794
1317
  const schedules = this.options.schedules;
795
1318
  if (schedules && schedules.length > 0) {
796
- await (0, import_nestjs_durable_core6.runSchedules)(this.engine, schedules, Date.now());
1319
+ await (0, import_nestjs_durable_core9.runSchedules)(this.engine, schedules, Date.now());
797
1320
  }
798
1321
  } finally {
799
1322
  this.polling = false;
800
1323
  }
801
1324
  }
802
1325
  };
803
- TimerPoller = _ts_decorate6([
804
- (0, import_common6.Injectable)(),
805
- _ts_param5(1, (0, import_common6.Inject)(import_nestjs_durable_core6.DURABLE_OPTIONS_CANONICAL)),
806
- _ts_metadata6("design:type", Function),
807
- _ts_metadata6("design:paramtypes", [
808
- typeof import_nestjs_durable_core6.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core6.WorkflowEngine,
1326
+ TimerPoller = _ts_decorate9([
1327
+ (0, import_common9.Injectable)(),
1328
+ _ts_param6(1, (0, import_common9.Inject)(import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL)),
1329
+ _ts_metadata9("design:type", Function),
1330
+ _ts_metadata9("design:paramtypes", [
1331
+ typeof import_nestjs_durable_core9.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core9.WorkflowEngine,
809
1332
  typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions
810
1333
  ])
811
1334
  ], TimerPoller);
812
1335
 
813
1336
  // src/tokens.ts
814
1337
  var CONTEXT_ACCESSOR = Symbol.for("@dudousxd/nestjs-context:accessor");
1338
+ var RUN_GATEWAY = Symbol.for("nestjs-durable:run-gateway");
815
1339
 
816
1340
  // src/workflow.registrar.ts
817
- var import_nestjs_durable_core7 = require("@dudousxd/nestjs-durable-core");
818
- var import_common7 = require("@nestjs/common");
1341
+ var import_nestjs_durable_core10 = require("@dudousxd/nestjs-durable-core");
1342
+ var import_common10 = require("@nestjs/common");
819
1343
  var import_core4 = require("@nestjs/core");
820
1344
 
821
1345
  // src/input-validation.ts
@@ -858,23 +1382,23 @@ function isStepInterceptor(target) {
858
1382
  __name(isStepInterceptor, "isStepInterceptor");
859
1383
 
860
1384
  // src/workflow.registrar.ts
861
- function _ts_decorate7(decorators, target, key, desc) {
1385
+ function _ts_decorate10(decorators, target, key, desc) {
862
1386
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
863
1387
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
864
1388
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
865
1389
  return c > 3 && r && Object.defineProperty(target, key, r), r;
866
1390
  }
867
- __name(_ts_decorate7, "_ts_decorate");
868
- function _ts_metadata7(k, v) {
1391
+ __name(_ts_decorate10, "_ts_decorate");
1392
+ function _ts_metadata10(k, v) {
869
1393
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
870
1394
  }
871
- __name(_ts_metadata7, "_ts_metadata");
872
- function _ts_param6(paramIndex, decorator) {
1395
+ __name(_ts_metadata10, "_ts_metadata");
1396
+ function _ts_param7(paramIndex, decorator) {
873
1397
  return function(target, key) {
874
1398
  decorator(target, key, paramIndex);
875
1399
  };
876
1400
  }
877
- __name(_ts_param6, "_ts_param");
1401
+ __name(_ts_param7, "_ts_param");
878
1402
  var WorkflowRegistrar = class {
879
1403
  static {
880
1404
  __name(this, "WorkflowRegistrar");
@@ -894,13 +1418,15 @@ var WorkflowRegistrar = class {
894
1418
  this.inAppWorker = inAppWorker;
895
1419
  }
896
1420
  async onApplicationBootstrap() {
897
- if (this.options.worker === false) return;
1421
+ if (!isDrivingOperator(this.options)) return;
898
1422
  await this.engine.recoverIncomplete();
899
1423
  }
900
1424
  /** On deploy/shutdown: stop picking up new runs and wait for in-flight ones to settle, then close
901
1425
  * the transport(s) so the broker workers stop consuming and connections are released. Closing
902
- * AFTER the drain keeps the transport alive while in-flight runs dispatch/await their remote steps. */
1426
+ * AFTER the drain keeps the transport alive while in-flight runs dispatch/await their remote steps.
1427
+ * Operator only — a thin worker (no `store`) holds no engine to drain. */
903
1428
  async onApplicationShutdown() {
1429
+ if (!isOperatorRole(this.options)) return;
904
1430
  await this.engine.drain(this.options.shutdownTimeoutMs);
905
1431
  const transports = [
906
1432
  this.options.transport,
@@ -909,8 +1435,13 @@ var WorkflowRegistrar = class {
909
1435
  await Promise.allSettled(transports.map((t) => t?.close?.()));
910
1436
  }
911
1437
  async onModuleInit() {
1438
+ if (!isOperatorRole(this.options)) return;
1439
+ const store = this.store;
1440
+ if (!store) {
1441
+ throw new Error("unreachable: STATE_STORE_CANONICAL must resolve a store when options.store is set");
1442
+ }
912
1443
  if (this.options.autoSchema !== false) {
913
- await this.store.ensureSchema?.();
1444
+ await store.ensureSchema?.();
914
1445
  }
915
1446
  const deadLetterByWorkflow = /* @__PURE__ */ new Map();
916
1447
  for (const wrapper of this.discovery.getProviders()) {
@@ -929,11 +1460,11 @@ var WorkflowRegistrar = class {
929
1460
  const validateInput = meta.validateInput ?? (meta.inputSchema ? classValidatorInput(meta.inputSchema) : void 0);
930
1461
  const eventBatch = meta.debounce ? {
931
1462
  mode: "debounce",
932
- windowMs: (0, import_nestjs_durable_core7.parseDuration)(meta.debounce)
1463
+ windowMs: (0, import_nestjs_durable_core10.parseDuration)(meta.debounce)
933
1464
  } : meta.batch ? {
934
1465
  mode: "batch",
935
1466
  maxSize: meta.batch.maxSize,
936
- windowMs: (0, import_nestjs_durable_core7.parseDuration)(meta.batch.within)
1467
+ windowMs: (0, import_nestjs_durable_core10.parseDuration)(meta.batch.within)
937
1468
  } : void 0;
938
1469
  const workflowCtor = workflow.constructor;
939
1470
  this.engine.register(meta.name, meta.version, (ctx, input) => workflow.run(ctx, input), {
@@ -944,11 +1475,17 @@ var WorkflowRegistrar = class {
944
1475
  onEvent: getOnEvents(meta, workflowCtor),
945
1476
  eventBatch,
946
1477
  // Uniform dispatch (opt-in): when an in-app worker is configured, register the body GROUP-SERVED
947
- // so the engine dispatches its turns to the app's own group instead of running it inline; the
948
- // co-located worker consumer replays the same body. Absent → the inline fast path (unchanged).
1478
+ // so the engine dispatches its turns over the transport instead of running it inline; the
1479
+ // co-located worker consumer (Task 5: one queue PER REGISTERED NAME) replays the same body.
1480
+ // The routing token — and the executor that dispatches under it — MUST be keyed by THIS
1481
+ // workflow's own name (`tenantGroup(sanitizeQueueToken(meta.name), partition)`), not a single
1482
+ // group shared across every discovered `@Workflow`: a fixed shared token would dispatch every
1483
+ // workflow's turns to one queue while the co-located worker subscribes one queue per name,
1484
+ // so a turn dispatched under the wrong token would never be consumed. Absent → the inline fast
1485
+ // path (unchanged).
949
1486
  ...this.inAppWorker ? {
950
- group: this.inAppWorker.group,
951
- executor: this.inAppWorker.executor
1487
+ group: (0, import_nestjs_durable_core10.tenantGroup)((0, import_nestjs_durable_core10.sanitizeQueueToken)(meta.name), this.inAppWorker.partition),
1488
+ executor: new import_nestjs_durable_core10.RemoteWorkflowExecutor(this.inAppWorker.transport, meta.name, this.inAppWorker.partition)
952
1489
  } : {}
953
1490
  });
954
1491
  const inline = this.findDeadLetterHandler(workflow);
@@ -960,7 +1497,7 @@ var WorkflowRegistrar = class {
960
1497
  this.engine.register(dlqName, meta.version, inline);
961
1498
  deadLetterByWorkflow.set(meta.name, dlqName);
962
1499
  } else if (meta.deadLetterWorkflow) {
963
- deadLetterByWorkflow.set(meta.name, (0, import_nestjs_durable_core7.workflowName)(meta.deadLetterWorkflow));
1500
+ deadLetterByWorkflow.set(meta.name, (0, import_nestjs_durable_core10.workflowName)(meta.deadLetterWorkflow));
964
1501
  }
965
1502
  });
966
1503
  this.installDeadLetterRouting(deadLetterByWorkflow);
@@ -982,31 +1519,40 @@ var WorkflowRegistrar = class {
982
1519
  * a `dlq:<runId>` id, so re-recovery never double-dispatches.
983
1520
  */
984
1521
  installDeadLetterRouting(byWorkflow) {
985
- const fallback = this.options.deadLetterWorkflow ? (0, import_nestjs_durable_core7.workflowName)(this.options.deadLetterWorkflow) : void 0;
1522
+ const fallback = this.options.deadLetterWorkflow ? (0, import_nestjs_durable_core10.workflowName)(this.options.deadLetterWorkflow) : void 0;
986
1523
  if (byWorkflow.size === 0 && !fallback) return;
987
1524
  this.engine.onDead((run) => {
988
1525
  const target = byWorkflow.get(run.workflow) ?? fallback;
989
1526
  if (!target) return;
990
- void this.engine.start(target, {
991
- deadRunId: run.id,
992
- workflow: run.workflow,
993
- input: run.input,
994
- error: run.error
995
- }, `dlq:${run.id}`).catch(() => void 0);
1527
+ void this.engine.start(
1528
+ target,
1529
+ {
1530
+ deadRunId: run.id,
1531
+ workflow: run.workflow,
1532
+ input: run.input,
1533
+ error: run.error
1534
+ },
1535
+ `dlq:${run.id}`,
1536
+ // Route the dead-letter handler to the dead run's OWN tenant so an operator dispatches it to
1537
+ // that tenant's worker group (`target@<tenant>`), not the bare group.
1538
+ {
1539
+ namespace: run.namespace
1540
+ }
1541
+ ).catch(() => void 0);
996
1542
  });
997
1543
  }
998
1544
  };
999
- WorkflowRegistrar = _ts_decorate7([
1000
- (0, import_common7.Injectable)(),
1001
- _ts_param6(3, (0, import_common7.Inject)(import_nestjs_durable_core7.STATE_STORE_CANONICAL)),
1002
- _ts_param6(4, (0, import_common7.Inject)(import_nestjs_durable_core7.DURABLE_OPTIONS_CANONICAL)),
1003
- _ts_param6(5, (0, import_common7.Inject)(IN_APP_WORKER_BINDING)),
1004
- _ts_metadata7("design:type", Function),
1005
- _ts_metadata7("design:paramtypes", [
1545
+ WorkflowRegistrar = _ts_decorate10([
1546
+ (0, import_common10.Injectable)(),
1547
+ _ts_param7(3, (0, import_common10.Inject)(import_nestjs_durable_core10.STATE_STORE_CANONICAL)),
1548
+ _ts_param7(4, (0, import_common10.Inject)(import_nestjs_durable_core10.DURABLE_OPTIONS_CANONICAL)),
1549
+ _ts_param7(5, (0, import_common10.Inject)(IN_APP_WORKER_BINDING)),
1550
+ _ts_metadata10("design:type", Function),
1551
+ _ts_metadata10("design:paramtypes", [
1006
1552
  typeof import_core4.DiscoveryService === "undefined" ? Object : import_core4.DiscoveryService,
1007
1553
  typeof import_core4.MetadataScanner === "undefined" ? Object : import_core4.MetadataScanner,
1008
- typeof import_nestjs_durable_core7.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core7.WorkflowEngine,
1009
- typeof StateStore === "undefined" ? Object : StateStore,
1554
+ typeof import_nestjs_durable_core10.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core10.WorkflowEngine,
1555
+ Object,
1010
1556
  typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions,
1011
1557
  Object
1012
1558
  ])
@@ -1014,19 +1560,19 @@ WorkflowRegistrar = _ts_decorate7([
1014
1560
 
1015
1561
  // src/workflow.service.ts
1016
1562
  var import_node_crypto = require("crypto");
1017
- var import_nestjs_durable_core8 = require("@dudousxd/nestjs-durable-core");
1018
- var import_common8 = require("@nestjs/common");
1019
- function _ts_decorate8(decorators, target, key, desc) {
1563
+ var import_nestjs_durable_core11 = require("@dudousxd/nestjs-durable-core");
1564
+ var import_common11 = require("@nestjs/common");
1565
+ function _ts_decorate11(decorators, target, key, desc) {
1020
1566
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1021
1567
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1022
1568
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1023
1569
  return c > 3 && r && Object.defineProperty(target, key, r), r;
1024
1570
  }
1025
- __name(_ts_decorate8, "_ts_decorate");
1026
- function _ts_metadata8(k, v) {
1571
+ __name(_ts_decorate11, "_ts_decorate");
1572
+ function _ts_metadata11(k, v) {
1027
1573
  if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1028
1574
  }
1029
- __name(_ts_metadata8, "_ts_metadata");
1575
+ __name(_ts_metadata11, "_ts_metadata");
1030
1576
  var WorkflowService = class {
1031
1577
  static {
1032
1578
  __name(this, "WorkflowService");
@@ -1066,22 +1612,32 @@ var WorkflowService = class {
1066
1612
  return this.engine.publishEvent(name, payload, opts);
1067
1613
  }
1068
1614
  };
1069
- WorkflowService = _ts_decorate8([
1070
- (0, import_common8.Injectable)(),
1071
- _ts_metadata8("design:type", Function),
1072
- _ts_metadata8("design:paramtypes", [
1073
- typeof import_nestjs_durable_core8.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core8.WorkflowEngine
1615
+ WorkflowService = _ts_decorate11([
1616
+ (0, import_common11.Injectable)(),
1617
+ _ts_metadata11("design:type", Function),
1618
+ _ts_metadata11("design:paramtypes", [
1619
+ typeof import_nestjs_durable_core11.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core11.WorkflowEngine
1074
1620
  ])
1075
1621
  ], WorkflowService);
1076
1622
 
1077
1623
  // src/durable.module.ts
1078
- function _ts_decorate9(decorators, target, key, desc) {
1624
+ function _ts_decorate12(decorators, target, key, desc) {
1079
1625
  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1080
1626
  if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1081
1627
  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1082
1628
  return c > 3 && r && Object.defineProperty(target, key, r), r;
1083
1629
  }
1084
- __name(_ts_decorate9, "_ts_decorate");
1630
+ __name(_ts_decorate12, "_ts_decorate");
1631
+ function _ts_metadata12(k, v) {
1632
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1633
+ }
1634
+ __name(_ts_metadata12, "_ts_metadata");
1635
+ function _ts_param8(paramIndex, decorator) {
1636
+ return function(target, key) {
1637
+ decorator(target, key, paramIndex);
1638
+ };
1639
+ }
1640
+ __name(_ts_param8, "_ts_param");
1085
1641
  function resolveAccessor(moduleRef) {
1086
1642
  try {
1087
1643
  return moduleRef.get(CONTEXT_ACCESSOR, {
@@ -1121,20 +1677,103 @@ function isControlPlane(x) {
1121
1677
  return !!x && typeof x.publishControl === "function" && typeof x.onControl === "function";
1122
1678
  }
1123
1679
  __name(isControlPlane, "isControlPlane");
1680
+ function isScopeableStore(store) {
1681
+ return typeof store.withScope === "function";
1682
+ }
1683
+ __name(isScopeableStore, "isScopeableStore");
1684
+ function scopedStore(store, options) {
1685
+ if (options.scopeReads !== true || options.namespace === void 0) return store;
1686
+ if (!isScopeableStore(store)) return store;
1687
+ return store.withScope({
1688
+ namespace: options.namespace
1689
+ });
1690
+ }
1691
+ __name(scopedStore, "scopedStore");
1692
+ function assertValidRole(options) {
1693
+ const hasStore = options.store !== void 0;
1694
+ const hasConnection = options.connection !== void 0;
1695
+ if (!hasStore && !hasConnection) {
1696
+ throw new Error("a durable module needs either a `store` (operator) or a `connection` (worker)");
1697
+ }
1698
+ if (hasStore && options.transport === void 0) {
1699
+ throw new Error("an operator (`store`) needs a `transport`");
1700
+ }
1701
+ }
1702
+ __name(assertValidRole, "assertValidRole");
1703
+ var RunGatewayBootstrap = class RunGatewayBootstrap2 {
1704
+ static {
1705
+ __name(this, "RunGatewayBootstrap");
1706
+ }
1707
+ engine;
1708
+ transport;
1709
+ gateway;
1710
+ store;
1711
+ options;
1712
+ unsubscribe;
1713
+ constructor(engine, transport, gateway, store, options) {
1714
+ this.engine = engine;
1715
+ this.transport = transport;
1716
+ this.gateway = gateway;
1717
+ this.store = store;
1718
+ this.options = options;
1719
+ }
1720
+ onApplicationBootstrap() {
1721
+ if (!isDrivingOperator(this.options) || !this.transport) return;
1722
+ const store = this.store;
1723
+ if (!store) return;
1724
+ const { onRunRequest, publishRunReply, publishTenantEvent } = this.transport;
1725
+ if (typeof onRunRequest === "function" && typeof publishRunReply === "function") {
1726
+ const runRequestTransport = {
1727
+ onRunRequest: onRunRequest.bind(this.transport),
1728
+ publishRunReply: publishRunReply.bind(this.transport)
1729
+ };
1730
+ new RunRequestResponder(runRequestTransport, this.gateway).start();
1731
+ }
1732
+ if (typeof publishTenantEvent === "function") {
1733
+ const republisher = new TenantEventRepublisher(store, publishTenantEvent.bind(this.transport));
1734
+ this.unsubscribe = this.engine.subscribe((event) => {
1735
+ void republisher.handle(event);
1736
+ });
1737
+ }
1738
+ }
1739
+ onModuleDestroy() {
1740
+ this.unsubscribe?.();
1741
+ }
1742
+ };
1743
+ RunGatewayBootstrap = _ts_decorate12([
1744
+ (0, import_common12.Injectable)(),
1745
+ _ts_param8(1, (0, import_common12.Inject)(import_nestjs_durable_core12.TRANSPORT_CANONICAL)),
1746
+ _ts_param8(2, (0, import_common12.Inject)(RUN_GATEWAY)),
1747
+ _ts_param8(3, (0, import_common12.Inject)(import_nestjs_durable_core12.STATE_STORE_CANONICAL)),
1748
+ _ts_param8(4, (0, import_common12.Inject)(import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL)),
1749
+ _ts_metadata12("design:type", Function),
1750
+ _ts_metadata12("design:paramtypes", [
1751
+ typeof import_nestjs_durable_core12.WorkflowEngine === "undefined" ? Object : import_nestjs_durable_core12.WorkflowEngine,
1752
+ Object,
1753
+ typeof RunGateway === "undefined" ? Object : RunGateway,
1754
+ Object,
1755
+ typeof DurableModuleOptions === "undefined" ? Object : DurableModuleOptions
1756
+ ])
1757
+ ], RunGatewayBootstrap);
1124
1758
  var DurableModule = class _DurableModule {
1125
1759
  static {
1126
1760
  __name(this, "DurableModule");
1127
1761
  }
1128
1762
  static forRoot(options) {
1763
+ assertValidRole(options);
1129
1764
  return _DurableModule.build({
1130
- provide: import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL,
1765
+ provide: import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL,
1131
1766
  useValue: options
1132
1767
  });
1133
1768
  }
1134
1769
  static forRootAsync(options) {
1135
1770
  return _DurableModule.build({
1136
- provide: import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL,
1137
- useFactory: options.useFactory,
1771
+ provide: import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL,
1772
+ useFactory: /* @__PURE__ */ __name(async (...args) => {
1773
+ const resolved = await options.useFactory(...args);
1774
+ assertValidRole(resolved);
1775
+ return resolved;
1776
+ }, "useFactory"),
1138
1777
  inject: options.inject ?? []
1139
1778
  });
1140
1779
  }
@@ -1148,71 +1787,83 @@ var DurableModule = class _DurableModule {
1148
1787
  providers: [
1149
1788
  optionsProvider,
1150
1789
  {
1151
- provide: import_nestjs_durable_core9.STATE_STORE_CANONICAL,
1152
- useFactory: /* @__PURE__ */ __name((options) => options.store, "useFactory"),
1790
+ provide: import_nestjs_durable_core12.STATE_STORE_CANONICAL,
1791
+ useFactory: /* @__PURE__ */ __name((options) => options.store !== void 0 ? scopedStore(options.store, options) : null, "useFactory"),
1153
1792
  inject: [
1154
- import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL
1793
+ import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL
1155
1794
  ]
1156
1795
  },
1157
1796
  {
1158
- provide: import_nestjs_durable_core9.TRANSPORT_CANONICAL,
1797
+ provide: import_nestjs_durable_core12.TRANSPORT_CANONICAL,
1159
1798
  useFactory: /* @__PURE__ */ __name((options) => options.transport ?? null, "useFactory"),
1160
1799
  inject: [
1161
- import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL
1800
+ import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL
1162
1801
  ]
1163
1802
  },
1164
1803
  // Legacy back-compat aliases (deprecated tokens still resolve to the same instances):
1165
1804
  {
1166
- provide: import_nestjs_durable_core9.STATE_STORE,
1167
- useExisting: import_nestjs_durable_core9.STATE_STORE_CANONICAL
1805
+ provide: import_nestjs_durable_core12.STATE_STORE,
1806
+ useExisting: import_nestjs_durable_core12.STATE_STORE_CANONICAL
1168
1807
  },
1169
1808
  {
1170
- provide: import_nestjs_durable_core9.TRANSPORT,
1171
- useExisting: import_nestjs_durable_core9.TRANSPORT_CANONICAL
1809
+ provide: import_nestjs_durable_core12.TRANSPORT,
1810
+ useExisting: import_nestjs_durable_core12.TRANSPORT_CANONICAL
1172
1811
  },
1173
1812
  {
1174
- provide: import_nestjs_durable_core9.DURABLE_OPTIONS,
1175
- useExisting: import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL
1813
+ provide: import_nestjs_durable_core12.DURABLE_OPTIONS,
1814
+ useExisting: import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL
1176
1815
  },
1177
1816
  {
1178
- provide: import_nestjs_durable_core9.WorkflowEngine,
1179
- useFactory: /* @__PURE__ */ __name(async (store, transport, opts, moduleRef) => {
1180
- const primary = transport ?? opts.transports?.[0]?.transport;
1817
+ // Shared token, bound EXACTLY once: a real engine for the operator role, or a store-less
1818
+ // `DurableStartClient` facade for a thin worker (no `store`) — either way, `WorkflowService`
1819
+ // and app code call `engine.start(...)` unchanged.
1820
+ provide: import_nestjs_durable_core12.WorkflowEngine,
1821
+ useFactory: /* @__PURE__ */ __name(async (options, store, transport, moduleRef) => {
1822
+ if (options.store === void 0) {
1823
+ return new DurableStartClient(options);
1824
+ }
1825
+ if (!store) {
1826
+ throw new Error("unreachable: STATE_STORE_CANONICAL must resolve a store when options.store is set");
1827
+ }
1828
+ const primary = transport ?? options.transports?.[0]?.transport;
1181
1829
  const accessor = resolveAccessor(moduleRef);
1182
- const context = opts.context ?? (accessor ? () => carrierFromAccessor(accessor) : void 0);
1830
+ const context = options.context ?? (accessor ? () => carrierFromAccessor(accessor) : void 0);
1183
1831
  const runtime = accessor ? await resolveContextRuntime() : void 0;
1184
1832
  const rehydrate = runtime && ((carrier, fn) => carrier && Object.keys(carrier).length > 0 ? runtime.deserialize(carrier, fn) : fn());
1185
- const engine = new import_nestjs_durable_core9.WorkflowEngine({
1833
+ const engine = new import_nestjs_durable_core12.WorkflowEngine({
1186
1834
  store,
1187
1835
  transport: transport ?? void 0,
1188
- transports: opts.transports,
1189
- controlPlane: opts.controlPlane ?? (isControlPlane(primary) ? primary : void 0),
1190
- leaseMs: opts.leaseMs,
1191
- admission: opts.admission,
1192
- maxRecoveryAttempts: opts.maxRecoveryAttempts,
1193
- remoteAdvanceSilenceMs: opts.remoteAdvanceSilenceMs,
1194
- instanceId: opts.instanceId,
1195
- namespace: opts.namespace,
1196
- webhookUrl: opts.webhookUrl,
1197
- traceparent: opts.traceparent,
1836
+ transports: options.transports,
1837
+ controlPlane: options.controlPlane ?? (isControlPlane(primary) ? primary : void 0),
1838
+ leaseMs: options.leaseMs,
1839
+ admission: options.admission,
1840
+ maxRecoveryAttempts: options.maxRecoveryAttempts,
1841
+ remoteAdvanceSilenceMs: options.remoteAdvanceSilenceMs,
1842
+ instanceId: options.instanceId,
1843
+ namespace: options.namespace,
1844
+ webhookUrl: options.webhookUrl,
1845
+ traceparent: options.traceparent,
1198
1846
  context,
1199
1847
  rehydrate: rehydrate || void 0,
1200
- compensationRetries: opts.compensationRetries,
1201
- // A non-worker (API/dashboard) instance must not run workflows: enqueue-only, leaving
1202
- // each `pending` run in the store for a worker's `runPending` poll. Workers use the
1203
- // default in-process dispatcher (execute locally).
1204
- runDispatcher: opts.worker === false ? {
1848
+ compensationRetries: options.compensationRetries,
1849
+ // A non-driving (dashboard/API) operator must not run workflows: enqueue-only, leaving
1850
+ // each `pending` run in the store for a DRIVING instance's poll. A driving operator gets
1851
+ // the engine's default in-process dispatcher: for a body registered inline, it runs
1852
+ // locally; for one registered GROUP-SERVED (co-located worker) or left unregistered, the
1853
+ // SAME default dispatcher routes it out remotely (group-served executor, or convention
1854
+ // dispatch — always on) instead.
1855
+ runDispatcher: options.drive === false ? {
1205
1856
  dispatch: /* @__PURE__ */ __name(() => {
1206
1857
  }, "dispatch")
1207
1858
  } : void 0
1208
1859
  });
1209
- for (const queue of opts.queues ?? []) engine.registerQueue(queue);
1860
+ for (const queue of options.queues ?? []) engine.registerQueue(queue);
1210
1861
  return engine;
1211
1862
  }, "useFactory"),
1212
1863
  inject: [
1213
- import_nestjs_durable_core9.STATE_STORE_CANONICAL,
1214
- import_nestjs_durable_core9.TRANSPORT_CANONICAL,
1215
- import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL,
1864
+ import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL,
1865
+ import_nestjs_durable_core12.STATE_STORE_CANONICAL,
1866
+ import_nestjs_durable_core12.TRANSPORT_CANONICAL,
1216
1867
  import_core5.ModuleRef
1217
1868
  ]
1218
1869
  },
@@ -1222,53 +1873,82 @@ var DurableModule = class _DurableModule {
1222
1873
  DurableStepRegistrar,
1223
1874
  TimerPoller,
1224
1875
  RetentionPoller,
1225
- // In-app worker (uniform dispatch, opt-in): inert when `inAppWorker` is unset — the binding
1226
- // resolves to null and the bootstrap no-ops, so a plain DurableModule is unchanged.
1227
- ...inAppWorkerProviders()
1876
+ // Tenant run gateway: bound EXACTLY once — the store-backed `StoreRunGateway` for an operator,
1877
+ // or (for a thin worker, no `store`) a `ProxyRunGateway` over `transport` when given, else a
1878
+ // gateway whose every method rejects with a clear tenant error.
1879
+ {
1880
+ provide: RUN_GATEWAY,
1881
+ useFactory: /* @__PURE__ */ __name((options, store, engine) => {
1882
+ if (options.store !== void 0) {
1883
+ if (!store) {
1884
+ throw new Error("unreachable: STATE_STORE_CANONICAL must resolve a store when options.store is set");
1885
+ }
1886
+ return new StoreRunGateway(store, engine);
1887
+ }
1888
+ return options.transport ? new ProxyRunGateway(options.transport, options.partition ?? "default", options.runGatewayTimeoutMs) : unavailableRunGateway();
1889
+ }, "useFactory"),
1890
+ inject: [
1891
+ import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL,
1892
+ import_nestjs_durable_core12.STATE_STORE_CANONICAL,
1893
+ import_nestjs_durable_core12.WorkflowEngine
1894
+ ]
1895
+ },
1896
+ RunGatewayBootstrap,
1897
+ // Co-located in-app worker (uniform dispatch): inert unless BOTH `store` and `connection` are
1898
+ // set — see `in-app-worker.ts`.
1899
+ ...inAppWorkerProviders(),
1900
+ // Pure thin-worker consumer: inert unless `connection` is set WITHOUT `store` — see
1901
+ // `durable-worker.module.ts`.
1902
+ ...thinWorkerProviders()
1228
1903
  ],
1229
1904
  exports: [
1230
1905
  WorkflowService,
1231
1906
  EntityService,
1232
- import_nestjs_durable_core9.WorkflowEngine,
1233
- import_nestjs_durable_core9.STATE_STORE,
1234
- import_nestjs_durable_core9.STATE_STORE_CANONICAL,
1235
- import_nestjs_durable_core9.TRANSPORT,
1236
- import_nestjs_durable_core9.TRANSPORT_CANONICAL,
1237
- import_nestjs_durable_core9.DURABLE_OPTIONS_CANONICAL
1907
+ import_nestjs_durable_core12.WorkflowEngine,
1908
+ import_nestjs_durable_core12.STATE_STORE,
1909
+ import_nestjs_durable_core12.STATE_STORE_CANONICAL,
1910
+ import_nestjs_durable_core12.TRANSPORT,
1911
+ import_nestjs_durable_core12.TRANSPORT_CANONICAL,
1912
+ import_nestjs_durable_core12.DURABLE_OPTIONS_CANONICAL,
1913
+ RUN_GATEWAY
1238
1914
  ]
1239
1915
  };
1240
1916
  }
1241
1917
  };
1242
- DurableModule = _ts_decorate9([
1243
- (0, import_common9.Module)({})
1918
+ DurableModule = _ts_decorate12([
1919
+ (0, import_common12.Module)({})
1244
1920
  ], DurableModule);
1245
1921
  // Annotate the CommonJS export names for ESM import in node:
1246
1922
  0 && (module.exports = {
1247
1923
  CONTEXT_ACCESSOR,
1248
1924
  DEAD_LETTER_METADATA,
1249
1925
  DURABLE_STEP_METADATA,
1250
- DURABLE_WORKER_OPTIONS,
1251
1926
  DURABLE_WORKER_RUNNERS,
1252
1927
  DeadLetter,
1253
1928
  DurableModule,
1929
+ DurableStartClient,
1254
1930
  DurableStep,
1255
- DurableWorkerModule,
1256
1931
  ENTITY_METADATA,
1257
1932
  ENTITY_ON_METADATA,
1258
1933
  Entity,
1259
1934
  EntityService,
1260
1935
  IN_APP_RUN_REDIS_WORKER,
1261
1936
  IN_APP_WORKER_BINDING,
1262
- IN_APP_WORKER_OPTIONS,
1263
1937
  IN_APP_WORKER_RUNNERS,
1264
1938
  IN_APP_WORKER_RUNTIME,
1265
1939
  InAppWorkerBootstrap,
1266
1940
  ON_EVENT_METADATA,
1267
1941
  On,
1268
1942
  OnEvent,
1943
+ ProxyRunGateway,
1944
+ RUN_GATEWAY,
1269
1945
  RUN_REDIS_WORKER,
1946
+ RunRequestResponder,
1270
1947
  STEP_INTERCEPTOR_METADATA,
1948
+ Step,
1271
1949
  StepInterceptor,
1950
+ StoreRunGateway,
1951
+ TenantEventRepublisher,
1272
1952
  ThinStepRegistrar,
1273
1953
  ThinWorkerBootstrap,
1274
1954
  ThinWorkflowRegistrar,
@@ -1282,6 +1962,10 @@ DurableModule = _ts_decorate9([
1282
1962
  getWorkflowMeta,
1283
1963
  inAppWorkerProviders,
1284
1964
  isDeadLetterHandler,
1285
- isStepInterceptor
1965
+ isDrivingOperator,
1966
+ isOperatorRole,
1967
+ isStepInterceptor,
1968
+ thinWorkerProviders,
1969
+ unavailableRunGateway
1286
1970
  });
1287
1971
  //# sourceMappingURL=index.cjs.map