@cadenza.io/core 1.10.1 → 1.11.1

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.mjs CHANGED
@@ -1,3 +1,38 @@
1
+ // src/utils/tools.ts
2
+ function deepCloneFilter(input, filterOut = () => false) {
3
+ if (input === null || typeof input !== "object") {
4
+ return input;
5
+ }
6
+ const visited = /* @__PURE__ */ new WeakMap();
7
+ const stack = [];
8
+ const output = Array.isArray(input) ? [] : {};
9
+ stack.push({ source: input, target: output });
10
+ visited.set(input, output);
11
+ while (stack.length) {
12
+ const { source, target, key } = stack.pop();
13
+ const currentTarget = key !== void 0 ? target[key] : target;
14
+ for (const [k, value] of Object.entries(source)) {
15
+ if (filterOut(k)) continue;
16
+ if (value && typeof value === "object") {
17
+ if (visited.has(value)) {
18
+ currentTarget[k] = visited.get(value);
19
+ continue;
20
+ }
21
+ const clonedValue = Array.isArray(value) ? [] : {};
22
+ currentTarget[k] = clonedValue;
23
+ visited.set(value, clonedValue);
24
+ stack.push({ source: value, target: currentTarget, key: k });
25
+ } else {
26
+ currentTarget[k] = value;
27
+ }
28
+ }
29
+ }
30
+ return output;
31
+ }
32
+ function formatTimestamp(timestamp) {
33
+ return new Date(timestamp).toISOString();
34
+ }
35
+
1
36
  // src/engine/SignalBroker.ts
2
37
  var SignalBroker = class _SignalBroker {
3
38
  // execId -> emitted signals
@@ -64,8 +99,11 @@ var SignalBroker = class _SignalBroker {
64
99
  },
65
100
  "Executes queued signals and clears the stack",
66
101
  500,
67
- { maxWait: 1e4 }
68
- ).doOn("meta.process_signal_queue_requested");
102
+ {
103
+ maxWait: 1e4,
104
+ leading: true
105
+ }
106
+ ).doOn("meta.process_signal_queue_requested").emitsAfter("meta.signal_broker.queue_empty");
69
107
  this.getSignalsTask = Cadenza.createMetaTask("Get signals", (ctx) => {
70
108
  return {
71
109
  __signals: Array.from(this.signalObservers.keys()),
@@ -107,6 +145,7 @@ var SignalBroker = class _SignalBroker {
107
145
  */
108
146
  emit(signal, context = {}) {
109
147
  const execId = context.__routineExecId || "global";
148
+ delete context.__routineExecId;
110
149
  if (!this.emitStacks.has(execId)) this.emitStacks.set(execId, /* @__PURE__ */ new Map());
111
150
  const stack = this.emitStacks.get(execId);
112
151
  stack.set(signal, context);
@@ -119,30 +158,36 @@ var SignalBroker = class _SignalBroker {
119
158
  }
120
159
  }
121
160
  execute(signal, context) {
122
- const isMeta = signal.startsWith("meta");
123
- const emittedAt = Date.now();
124
- const data = {
125
- ...context,
126
- __signalEmission: {
161
+ const isMeta = signal.startsWith("meta.");
162
+ const isSubMeta = signal.startsWith("sub_meta.");
163
+ if (!isSubMeta && (!isMeta || this.debug)) {
164
+ const emittedAt = Date.now();
165
+ context.__signalEmission = {
127
166
  ...context.__signalEmission,
128
167
  signalName: signal,
129
- emittedAt,
168
+ emittedAt: formatTimestamp(emittedAt),
130
169
  isMeta
131
- }
132
- };
133
- let executed;
134
- executed = this.executeListener(signal, data);
135
- const parts = signal.slice(0, Math.max(signal.lastIndexOf(":"), signal.lastIndexOf("."))).split(".");
136
- for (let i = parts.length; i > 0; i--) {
137
- const parent = parts.slice(0, i).join(".");
138
- executed = executed || this.executeListener(parent + ".*", data);
170
+ };
171
+ } else if (isSubMeta) {
172
+ context.__isSubMeta = true;
173
+ delete context.__signalEmission;
174
+ } else {
175
+ delete context.__signalEmission;
139
176
  }
140
177
  if (this.debug) {
141
178
  console.log(
142
- `Emitted signal ${signal} with context ${JSON.stringify(data)}`,
143
- executed ? "\u2705" : "\u274C"
179
+ `Emitting signal ${signal} with context ${JSON.stringify(context)}`
144
180
  );
145
181
  }
182
+ let executed;
183
+ executed = this.executeListener(signal, context);
184
+ if (!isSubMeta) {
185
+ const parts = signal.slice(0, Math.max(signal.lastIndexOf(":"), signal.lastIndexOf("."))).split(".");
186
+ for (let i = parts.length; i > 0; i--) {
187
+ const parent = parts.slice(0, i).join(".");
188
+ executed = executed || this.executeListener(parent + ".*", context);
189
+ }
190
+ }
146
191
  return executed;
147
192
  }
148
193
  executeListener(signal, context) {
@@ -448,40 +493,6 @@ import { v4 as uuid3 } from "uuid";
448
493
 
449
494
  // src/graph/context/GraphContext.ts
450
495
  import { v4 as uuid2 } from "uuid";
451
-
452
- // src/utils/tools.ts
453
- function deepCloneFilter(input, filterOut = () => false) {
454
- if (input === null || typeof input !== "object") {
455
- return input;
456
- }
457
- const visited = /* @__PURE__ */ new WeakMap();
458
- const stack = [];
459
- const output = Array.isArray(input) ? [] : {};
460
- stack.push({ source: input, target: output });
461
- visited.set(input, output);
462
- while (stack.length) {
463
- const { source, target, key } = stack.pop();
464
- const currentTarget = key !== void 0 ? target[key] : target;
465
- for (const [k, value] of Object.entries(source)) {
466
- if (filterOut(k)) continue;
467
- if (value && typeof value === "object") {
468
- if (visited.has(value)) {
469
- currentTarget[k] = visited.get(value);
470
- continue;
471
- }
472
- const clonedValue = Array.isArray(value) ? [] : {};
473
- currentTarget[k] = clonedValue;
474
- visited.set(value, clonedValue);
475
- stack.push({ source: value, target: currentTarget, key: k });
476
- } else {
477
- currentTarget[k] = value;
478
- }
479
- }
480
- }
481
- return output;
482
- }
483
-
484
- // src/graph/context/GraphContext.ts
485
496
  var GraphContext = class _GraphContext {
486
497
  // __keys, frozen
487
498
  constructor(context) {
@@ -641,7 +652,10 @@ function sleep(ms) {
641
652
  // src/graph/execution/GraphNode.ts
642
653
  var GraphNode = class _GraphNode extends SignalEmitter {
643
654
  constructor(task, context, routineExecId, prevNodes = [], debug = false) {
644
- super(task.isMeta);
655
+ var _a;
656
+ super(
657
+ task.isMeta && !debug || task.isSubMeta || ((_a = context == null ? void 0 : context.getMetaData()) == null ? void 0 : _a.__isSubMeta)
658
+ );
645
659
  this.divided = false;
646
660
  this.splitGroupId = "";
647
661
  this.processing = false;
@@ -712,6 +726,7 @@ var GraphNode = class _GraphNode extends SignalEmitter {
712
726
  return this.task.getTag(this.context);
713
727
  }
714
728
  scheduleOn(layer) {
729
+ var _a;
715
730
  let shouldSchedule = true;
716
731
  const nodes = layer.getNodesByRoutineExecId(this.routineExecId);
717
732
  for (const node of nodes) {
@@ -728,23 +743,56 @@ var GraphNode = class _GraphNode extends SignalEmitter {
728
743
  if (shouldSchedule) {
729
744
  this.layer = layer;
730
745
  layer.add(this);
746
+ const context = this.context.getFullContext();
731
747
  const scheduledAt = Date.now();
732
748
  this.emitWithMetadata("meta.node.scheduled", {
733
- ...this.lightExport(),
734
- __scheduled: scheduledAt
749
+ data: {
750
+ uuid: this.id,
751
+ routineExecutionId: this.routineExecId,
752
+ contractId: context.__contractId,
753
+ context: this.context.export(),
754
+ taskId: this.task.id,
755
+ taskName: this.task.name,
756
+ isMeta: this.isMeta(),
757
+ isScheduled: true,
758
+ splitGroupId: this.splitGroupId,
759
+ created: formatTimestamp(scheduledAt)
760
+ }
735
761
  });
736
- const context = this.context.getFullContext();
737
- if (context.__signalEmission !== void 0 && (!this.isMeta() || this.debug)) {
762
+ this.previousNodes.forEach((node) => {
763
+ this.emitWithMetadata("meta.node.mapped", {
764
+ data: {
765
+ taskExecutionId: this.id,
766
+ previousTaskExecutionId: node.id,
767
+ executionCount: "increment"
768
+ },
769
+ filter: {
770
+ taskId: this.task.id,
771
+ previousTaskId: node.task.id
772
+ }
773
+ });
774
+ if (node.failed || node.errored) {
775
+ this.emitWithMetadata("meta.node.failed_mapped", {
776
+ data: {
777
+ executionCount: "increment"
778
+ },
779
+ filter: {
780
+ taskId: this.task.id,
781
+ failTaskId: node.task.id
782
+ }
783
+ });
784
+ }
785
+ });
786
+ if (((_a = context.__signalEmission) == null ? void 0 : _a.signalName) && (!this.isMeta() || this.debug)) {
738
787
  this.emitWithMetadata("meta.node.consumed_signal", {
739
- __signalConsumption: {
788
+ data: {
740
789
  signalName: context.__signalEmission.signalName,
741
790
  taskId: this.task.id,
742
791
  taskExecutionId: this.id,
743
- consumedAt: scheduledAt
792
+ consumedAt: formatTimestamp(scheduledAt)
744
793
  }
745
794
  });
746
795
  delete context.__signalEmission;
747
- this.migrate(context);
748
796
  }
749
797
  }
750
798
  }
@@ -752,14 +800,25 @@ var GraphNode = class _GraphNode extends SignalEmitter {
752
800
  if (this.executionStart === 0) {
753
801
  this.executionStart = Date.now();
754
802
  }
755
- const memento = this.lightExport();
756
803
  if (this.previousNodes.length === 0) {
757
- this.emitWithMetadata("meta.node.started_routine_execution", memento);
804
+ this.emitWithMetadata("meta.node.started_routine_execution", {
805
+ data: {
806
+ isRunning: true,
807
+ started: formatTimestamp(this.executionStart)
808
+ },
809
+ filter: { uuid: this.routineExecId }
810
+ });
758
811
  }
759
812
  if (this.debug) {
760
813
  this.log();
761
814
  }
762
- this.emitWithMetadata("meta.node.started", memento);
815
+ this.emitWithMetadata("meta.node.started", {
816
+ data: {
817
+ isRunning: true,
818
+ started: formatTimestamp(this.executionStart)
819
+ },
820
+ filter: { uuid: this.id }
821
+ });
763
822
  return this.executionStart;
764
823
  }
765
824
  end() {
@@ -769,15 +828,44 @@ var GraphNode = class _GraphNode extends SignalEmitter {
769
828
  this.processing = false;
770
829
  const end = Date.now();
771
830
  this.executionTime = end - this.executionStart;
772
- const memento = this.lightExport();
831
+ const context = this.context.getFullContext();
773
832
  if (this.errored || this.failed) {
774
- this.emitWithMetadata("meta.node.errored", memento);
833
+ this.emitWithMetadata("meta.node.errored", {
834
+ data: {
835
+ isRunning: false,
836
+ errored: this.errored,
837
+ failed: this.failed,
838
+ errorMessage: context.__error
839
+ },
840
+ filter: { uuid: this.id }
841
+ });
775
842
  }
776
- this.emitWithMetadata("meta.node.ended", memento);
843
+ this.emitWithMetadata("meta.node.ended", {
844
+ data: {
845
+ isRunning: false,
846
+ isComplete: true,
847
+ resultContext: this.context.export(),
848
+ errored: this.errored,
849
+ failed: this.failed,
850
+ errorMessage: context.__error,
851
+ progress: 1,
852
+ ended: formatTimestamp(end)
853
+ },
854
+ filter: { uuid: this.id }
855
+ });
777
856
  if (this.graphDone()) {
778
857
  this.emitWithMetadata(
779
858
  `meta.node.ended_routine_execution:${this.routineExecId}`,
780
- memento
859
+ {
860
+ data: {
861
+ isRunning: false,
862
+ isComplete: true,
863
+ resultContext: this.context.export(),
864
+ progress: 1,
865
+ ended: formatTimestamp(end)
866
+ },
867
+ filter: { uuid: this.routineExecId }
868
+ }
781
869
  );
782
870
  }
783
871
  return end;
@@ -839,23 +927,41 @@ var GraphNode = class _GraphNode extends SignalEmitter {
839
927
  }
840
928
  }
841
929
  emitWithMetadata(signal, ctx) {
842
- this.emit(signal, {
843
- ...ctx,
844
- __signalEmission: {
930
+ if (this.silent) return;
931
+ const data = { ...ctx };
932
+ if (!this.task.isHidden) {
933
+ data.__signalEmission = {
845
934
  taskId: this.task.id,
846
935
  taskExecutionId: this.id
847
- }
848
- });
936
+ };
937
+ data.__metadata = {
938
+ __routineExecId: this.routineExecId
939
+ };
940
+ }
941
+ this.emit(signal, data);
849
942
  }
850
943
  onProgress(progress) {
851
- var _a, _b, _c;
944
+ var _a, _b;
852
945
  progress = Math.min(Math.max(0, progress), 1);
853
- this.emitWithMetadata(`meta.node.progress:${this.routineExecId}`, {
854
- __nodeId: this.id,
855
- __routineExecId: this.routineExecId,
856
- __progress: progress,
857
- __weight: this.task.progressWeight / ((_c = (_b = (_a = this.layer) == null ? void 0 : _a.getNodesByRoutineExecId(this.routineExecId)) == null ? void 0 : _b.length) != null ? _c : 1)
946
+ this.emitWithMetadata("meta.node.progress", {
947
+ data: {
948
+ progress
949
+ },
950
+ filter: {
951
+ uuid: this.id
952
+ }
858
953
  });
954
+ this.emitWithMetadata(
955
+ `meta.node.routine_execution_progress:${this.routineExecId}`,
956
+ {
957
+ data: {
958
+ progress: progress * this.task.progressWeight / ((_b = (_a = this.layer) == null ? void 0 : _a.getIdenticalNodes(this).length) != null ? _b : 1)
959
+ },
960
+ filter: {
961
+ uuid: this.routineExecId
962
+ }
963
+ }
964
+ );
859
965
  }
860
966
  postProcess() {
861
967
  if (typeof this.result === "string") {
@@ -872,11 +978,11 @@ var GraphNode = class _GraphNode extends SignalEmitter {
872
978
  }
873
979
  if (this.errored || this.failed) {
874
980
  this.task.mapOnFailSignals(
875
- (signal) => this.emitWithMetadata(signal, this.context)
981
+ (signal) => this.emitWithMetadata(signal, this.context.getFullContext())
876
982
  );
877
983
  } else {
878
984
  this.task.mapSignals(
879
- (signal) => this.emitWithMetadata(signal, this.context)
985
+ (signal) => this.emitWithMetadata(signal, this.context.getFullContext())
880
986
  );
881
987
  }
882
988
  this.end();
@@ -1265,8 +1371,24 @@ var GraphRoutine = class extends SignalParticipant {
1265
1371
  this.name = name;
1266
1372
  this.description = description;
1267
1373
  this.isMeta = isMeta;
1268
- tasks.forEach((t) => this.tasks.add(t));
1269
- this.emit("meta.routine.created", { __routine: this });
1374
+ this.emit("meta.routine.created", {
1375
+ data: {
1376
+ uuid: this.id,
1377
+ name: this.name,
1378
+ description: this.description,
1379
+ isMeta: this.isMeta
1380
+ },
1381
+ __routineInstance: this
1382
+ });
1383
+ tasks.forEach((t) => {
1384
+ this.tasks.add(t);
1385
+ this.emit("meta.routine.task_added", {
1386
+ data: {
1387
+ taskId: t.id,
1388
+ routineId: this.id
1389
+ }
1390
+ });
1391
+ });
1270
1392
  }
1271
1393
  /**
1272
1394
  * Applies callback to starting tasks.
@@ -1296,7 +1418,10 @@ var GraphRoutine = class extends SignalParticipant {
1296
1418
  */
1297
1419
  destroy() {
1298
1420
  this.tasks.clear();
1299
- this.emit("meta.routine.destroyed", { __id: this.id });
1421
+ this.emit("meta.routine.destroyed", {
1422
+ data: { deleted: true },
1423
+ filter: { uuid: this.id }
1424
+ });
1300
1425
  }
1301
1426
  };
1302
1427
 
@@ -1346,6 +1471,8 @@ var Task = class extends SignalParticipant {
1346
1471
  * @param register Register via signal (default true).
1347
1472
  * @param isUnique
1348
1473
  * @param isMeta
1474
+ * @param isSubMeta
1475
+ * @param isHidden
1349
1476
  * @param getTagCallback
1350
1477
  * @param inputSchema
1351
1478
  * @param validateInputContext
@@ -1357,14 +1484,17 @@ var Task = class extends SignalParticipant {
1357
1484
  * @param retryDelayFactor
1358
1485
  * @edge Emits 'meta.task.created' with { __task: this } for seed.
1359
1486
  */
1360
- constructor(name, task, description = "", concurrency = 0, timeout = 0, register = true, isUnique = false, isMeta = false, getTagCallback = void 0, inputSchema = void 0, validateInputContext = false, outputSchema = void 0, validateOutputContext = false, retryCount = 0, retryDelay = 0, retryDelayMax = 0, retryDelayFactor = 1) {
1487
+ constructor(name, task, description = "", concurrency = 0, timeout = 0, register = true, isUnique = false, isMeta = false, isSubMeta = false, isHidden = false, getTagCallback = void 0, inputSchema = void 0, validateInputContext = false, outputSchema = void 0, validateOutputContext = false, retryCount = 0, retryDelay = 0, retryDelayMax = 0, retryDelayFactor = 1) {
1361
1488
  super();
1362
1489
  this.isMeta = false;
1490
+ this.isSubMeta = false;
1491
+ this.isHidden = false;
1363
1492
  this.isUnique = false;
1364
1493
  this.throttled = false;
1365
1494
  this.isSignal = false;
1366
1495
  this.isDeputy = false;
1367
1496
  this.isEphemeral = false;
1497
+ this.isDebounce = false;
1368
1498
  this.inputContextSchema = void 0;
1369
1499
  this.validateInputContext = false;
1370
1500
  this.outputContextSchema = void 0;
@@ -1387,6 +1517,8 @@ var Task = class extends SignalParticipant {
1387
1517
  this.timeout = timeout;
1388
1518
  this.isUnique = isUnique;
1389
1519
  this.isMeta = isMeta;
1520
+ this.isSubMeta = isSubMeta;
1521
+ this.isHidden = isHidden;
1390
1522
  this.inputContextSchema = inputSchema;
1391
1523
  this.validateInputContext = validateInputContext;
1392
1524
  this.outputContextSchema = outputSchema;
@@ -1399,8 +1531,35 @@ var Task = class extends SignalParticipant {
1399
1531
  this.getTag = (context) => getTagCallback(context, this);
1400
1532
  this.throttled = true;
1401
1533
  }
1402
- if (register) {
1403
- this.emit("meta.task.created", { __task: this });
1534
+ if (register && !this.isHidden && !this.isSubMeta) {
1535
+ const { __functionString, __getTagCallback } = this.export();
1536
+ this.emit("meta.task.created", {
1537
+ __task: {
1538
+ uuid: this.id,
1539
+ name: this.name,
1540
+ description: this.description,
1541
+ functionString: __functionString,
1542
+ tagIdGetter: __getTagCallback,
1543
+ layerIndex: this.layerIndex,
1544
+ concurrency: this.concurrency,
1545
+ retryCount: this.retryCount,
1546
+ retryDelay: this.retryDelay,
1547
+ retryDelayMax: this.retryDelayMax,
1548
+ retryDelayFactor: this.retryDelayFactor,
1549
+ timeout: this.timeout,
1550
+ isUnique: this.isUnique,
1551
+ isSignal: this.isSignal,
1552
+ isThrottled: this.throttled,
1553
+ isDebounce: this.isDebounce,
1554
+ isEphemeral: this.isEphemeral,
1555
+ isMeta: this.isMeta,
1556
+ validateInputContext: this.validateInputContext,
1557
+ validateOutputContext: this.validateOutputContext,
1558
+ inputContextSchemaId: this.inputContextSchema,
1559
+ outputContextSchemaId: this.outputContextSchema
1560
+ },
1561
+ __taskInstance: this
1562
+ });
1404
1563
  }
1405
1564
  }
1406
1565
  getTag(context) {
@@ -1610,6 +1769,12 @@ var Task = class extends SignalParticipant {
1610
1769
  this.decouple(pred);
1611
1770
  throw new Error(`Cycle adding pred ${pred.name} to ${this.name}`);
1612
1771
  }
1772
+ this.emit("meta.task.relationship_added", {
1773
+ data: {
1774
+ taskId: this.id,
1775
+ predecessorTaskId: pred.id
1776
+ }
1777
+ });
1613
1778
  }
1614
1779
  this.updateProgressWeights();
1615
1780
  return this;
@@ -1624,6 +1789,12 @@ var Task = class extends SignalParticipant {
1624
1789
  this.decouple(next);
1625
1790
  throw new Error(`Cycle adding next ${next.name} to ${this.name}`);
1626
1791
  }
1792
+ this.emit("meta.task.relationship_added", {
1793
+ data: {
1794
+ taskId: next.id,
1795
+ predecessorTaskId: this.id
1796
+ }
1797
+ });
1627
1798
  }
1628
1799
  this.updateProgressWeights();
1629
1800
  return this;
@@ -1649,6 +1820,12 @@ var Task = class extends SignalParticipant {
1649
1820
  this.decouple(task);
1650
1821
  throw new Error(`Cycle adding onFail ${task.name} to ${this.name}`);
1651
1822
  }
1823
+ this.emit("meta.task.on_fail_relationship_added", {
1824
+ data: {
1825
+ taskId: this.id,
1826
+ onFailTaskId: task.id
1827
+ }
1828
+ });
1652
1829
  }
1653
1830
  return this;
1654
1831
  }
@@ -1680,11 +1857,20 @@ var Task = class extends SignalParticipant {
1680
1857
  return layers;
1681
1858
  }
1682
1859
  updateLayerFromPredecessors() {
1860
+ const prevLayerIndex = this.layerIndex;
1683
1861
  let maxPred = 0;
1684
1862
  this.predecessorTasks.forEach(
1685
1863
  (pred) => maxPred = Math.max(maxPred, pred.layerIndex)
1686
1864
  );
1687
1865
  this.layerIndex = maxPred + 1;
1866
+ if (prevLayerIndex !== this.layerIndex) {
1867
+ this.emit("meta.task.layer_index_changed", {
1868
+ data: {
1869
+ layerIndex: this.layerIndex
1870
+ },
1871
+ filter: { uuid: this.id }
1872
+ });
1873
+ }
1688
1874
  const queue = Array.from(this.nextTasks);
1689
1875
  while (queue.length) {
1690
1876
  const next = queue.shift();
@@ -1724,7 +1910,10 @@ var Task = class extends SignalParticipant {
1724
1910
  this.predecessorTasks.clear();
1725
1911
  this.onFailTasks.clear();
1726
1912
  this.destroyed = true;
1727
- this.emit("meta.task.destroyed", { __id: this.id });
1913
+ this.emit("meta.task.destroyed", {
1914
+ data: { deleted: true },
1915
+ filter: { uuid: this.id }
1916
+ });
1728
1917
  }
1729
1918
  export() {
1730
1919
  return {
@@ -1772,10 +1961,11 @@ var GraphRegistry = class _GraphRegistry {
1772
1961
  this.registerTask = new Task(
1773
1962
  "Register task",
1774
1963
  (context) => {
1775
- const { __task } = context;
1776
- if (__task && !this.tasks.has(__task.id)) {
1777
- this.tasks.set(__task.id, __task);
1964
+ const { __taskInstance } = context;
1965
+ if (__taskInstance && !this.tasks.has(__taskInstance.id)) {
1966
+ this.tasks.set(__taskInstance.id, __taskInstance);
1778
1967
  }
1968
+ delete context.__taskInstance;
1779
1969
  return true;
1780
1970
  },
1781
1971
  "Registers tasks. Seed for meta.taskCreated",
@@ -1880,10 +2070,11 @@ var GraphRegistry = class _GraphRegistry {
1880
2070
  this.registerRoutine = Cadenza.createMetaTask(
1881
2071
  "Register routine",
1882
2072
  (context) => {
1883
- const { __routine } = context;
1884
- if (__routine && !this.routines.has(__routine.id)) {
1885
- this.routines.set(__routine.id, __routine);
2073
+ const { __routineInstance } = context;
2074
+ if (__routineInstance && !this.routines.has(__routineInstance.id)) {
2075
+ this.routines.set(__routineInstance.id, __routineInstance);
1886
2076
  }
2077
+ delete context.__routineInstance;
1887
2078
  return true;
1888
2079
  },
1889
2080
  "Registers routine."
@@ -2020,28 +2211,18 @@ var GraphRunner = class extends SignalEmitter {
2020
2211
  const ctx = new GraphContext(context || {});
2021
2212
  const routineExecId = (_a = context.__routineExecId) != null ? _a : uuid6();
2022
2213
  context.__routineExecId = routineExecId;
2023
- const data = {
2024
- __routineExecId: routineExecId,
2025
- __routineName: routineName,
2026
- __isMeta: isMeta,
2027
- __routineId: routineId,
2028
- __context: ctx.export(),
2029
- __previousRoutineExecution: (_c = (_b = context.__metaData) == null ? void 0 : _b.__routineExecId) != null ? _c : null,
2030
- __contractId: (_f = (_e = (_d = context.__metaData) == null ? void 0 : _d.__contractId) != null ? _e : context.__contractId) != null ? _f : null,
2031
- __task: {
2032
- __name: routineName
2033
- },
2034
- __scheduled: Date.now()
2035
- };
2036
- this.emit("meta.runner.added_tasks", data);
2037
- if (this.debug) {
2038
- console.log(
2039
- `${this.isMeta ? "Meta" : ""}Runner added tasks`,
2040
- allTasks.map((t) => t.name),
2041
- "with context",
2042
- ctx.getFullContext()
2043
- );
2044
- }
2214
+ this.emit("meta.runner.added_tasks", {
2215
+ data: {
2216
+ uuid: routineExecId,
2217
+ name: routineName,
2218
+ isMeta,
2219
+ contractId: (_d = (_c = (_b = context.__metaData) == null ? void 0 : _b.__contractId) != null ? _c : context.__contractId) != null ? _d : null,
2220
+ context: ctx.export(),
2221
+ previousRoutineExecution: (_f = (_e = context.__metaData) == null ? void 0 : _e.__routineExecId) != null ? _f : null,
2222
+ // TODO: There is a chance this is not added to the database yet...
2223
+ created: formatTimestamp(Date.now())
2224
+ }
2225
+ });
2045
2226
  allTasks.forEach(
2046
2227
  (task) => this.currentRun.addNode(
2047
2228
  new GraphNode(task, ctx, routineExecId, [], this.debug)
@@ -2112,7 +2293,7 @@ var GraphRunner = class extends SignalEmitter {
2112
2293
 
2113
2294
  // src/graph/definition/DebounceTask.ts
2114
2295
  var DebounceTask = class extends Task {
2115
- constructor(name, task, description = "", debounceTime = 1e3, leading = false, trailing = true, maxWait = 0, concurrency = 0, timeout = 0, register = true, isUnique = false, isMeta = false, inputSchema = void 0, validateInputSchema = false, outputSchema = void 0, validateOutputSchema = false) {
2296
+ constructor(name, task, description = "", debounceTime = 1e3, leading = false, trailing = true, maxWait = 0, concurrency = 0, timeout = 0, register = true, isUnique = false, isMeta = false, isSubMeta = false, isHidden = false, inputSchema = void 0, validateInputSchema = false, outputSchema = void 0, validateOutputSchema = false) {
2116
2297
  super(
2117
2298
  name,
2118
2299
  task,
@@ -2122,6 +2303,8 @@ var DebounceTask = class extends Task {
2122
2303
  register,
2123
2304
  isUnique,
2124
2305
  isMeta,
2306
+ isSubMeta,
2307
+ isHidden,
2125
2308
  void 0,
2126
2309
  inputSchema,
2127
2310
  validateInputSchema,
@@ -2231,7 +2414,7 @@ var DebounceTask = class extends Task {
2231
2414
 
2232
2415
  // src/graph/definition/EphemeralTask.ts
2233
2416
  var EphemeralTask = class extends Task {
2234
- constructor(name, task, description = "", once = true, condition = () => true, concurrency = 0, timeout = 0, register = false, isUnique = false, isMeta = false, getTagCallback = void 0, inputSchema = void 0, validateInputContext = false, outputSchema = void 0, validateOutputContext = false, retryCount = 0, retryDelay = 0, retryDelayMax = 0, retryDelayFactor = 1) {
2417
+ constructor(name, task, description = "", once = true, condition = () => true, concurrency = 0, timeout = 0, register = false, isUnique = false, isMeta = false, isSubMeta = false, isHidden = false, getTagCallback = void 0, inputSchema = void 0, validateInputContext = false, outputSchema = void 0, validateOutputContext = false, retryCount = 0, retryDelay = 0, retryDelayMax = 0, retryDelayFactor = 1) {
2235
2418
  super(
2236
2419
  name,
2237
2420
  task,
@@ -2241,6 +2424,8 @@ var EphemeralTask = class extends Task {
2241
2424
  register,
2242
2425
  isUnique,
2243
2426
  isMeta,
2427
+ isSubMeta,
2428
+ isHidden,
2244
2429
  getTagCallback,
2245
2430
  inputSchema,
2246
2431
  validateInputContext,
@@ -2257,7 +2442,7 @@ var EphemeralTask = class extends Task {
2257
2442
  }
2258
2443
  execute(context, emit, progressCallback) {
2259
2444
  const result = super.execute(context, emit, progressCallback);
2260
- if (this.once || !this.condition(result)) {
2445
+ if (this.once || this.condition(result)) {
2261
2446
  this.destroy();
2262
2447
  return result;
2263
2448
  }
@@ -2365,6 +2550,11 @@ var GraphLayer = class _GraphLayer extends ExecutionChain {
2365
2550
  getNodesByRoutineExecId(routineExecId) {
2366
2551
  return this.nodes.filter((node) => node.routineExecId === routineExecId);
2367
2552
  }
2553
+ getIdenticalNodes(node) {
2554
+ return this.nodes.filter(
2555
+ (n) => node.routineExecId === n.routineExecId && node.sharesTaskWith(n)
2556
+ );
2557
+ }
2368
2558
  isProcessed() {
2369
2559
  for (const node of this.nodes) {
2370
2560
  if (!node.isProcessed()) {
@@ -2838,6 +3028,8 @@ var Cadenza = class {
2838
3028
  register: true,
2839
3029
  isUnique: false,
2840
3030
  isMeta: false,
3031
+ isSubMeta: false,
3032
+ isHidden: false,
2841
3033
  getTagCallback: void 0,
2842
3034
  inputSchema: void 0,
2843
3035
  validateInputContext: false,
@@ -2859,6 +3051,8 @@ var Cadenza = class {
2859
3051
  options.register,
2860
3052
  options.isUnique,
2861
3053
  options.isMeta,
3054
+ options.isSubMeta,
3055
+ options.isHidden,
2862
3056
  options.getTagCallback,
2863
3057
  options.inputSchema,
2864
3058
  options.validateInputContext,
@@ -2886,6 +3080,8 @@ var Cadenza = class {
2886
3080
  register: true,
2887
3081
  isUnique: false,
2888
3082
  isMeta: true,
3083
+ isSubMeta: false,
3084
+ isHidden: false,
2889
3085
  getTagCallback: void 0,
2890
3086
  inputSchema: void 0,
2891
3087
  validateInputContext: false,
@@ -2915,6 +3111,8 @@ var Cadenza = class {
2915
3111
  register: true,
2916
3112
  isUnique: true,
2917
3113
  isMeta: false,
3114
+ isSubMeta: false,
3115
+ isHidden: false,
2918
3116
  getTagCallback: void 0,
2919
3117
  inputSchema: void 0,
2920
3118
  validateInputContext: false,
@@ -2942,6 +3140,8 @@ var Cadenza = class {
2942
3140
  register: true,
2943
3141
  isUnique: true,
2944
3142
  isMeta: true,
3143
+ isSubMeta: false,
3144
+ isHidden: false,
2945
3145
  getTagCallback: void 0,
2946
3146
  inputSchema: void 0,
2947
3147
  validateInputContext: false,
@@ -2971,6 +3171,8 @@ var Cadenza = class {
2971
3171
  register: true,
2972
3172
  isUnique: false,
2973
3173
  isMeta: false,
3174
+ isSubMeta: false,
3175
+ isHidden: false,
2974
3176
  inputSchema: void 0,
2975
3177
  validateInputContext: false,
2976
3178
  outputSchema: void 0,
@@ -2998,6 +3200,8 @@ var Cadenza = class {
2998
3200
  register: true,
2999
3201
  isUnique: false,
3000
3202
  isMeta: true,
3203
+ isSubMeta: false,
3204
+ isHidden: false,
3001
3205
  inputSchema: void 0,
3002
3206
  validateInputContext: false,
3003
3207
  outputSchema: void 0,
@@ -3035,6 +3239,8 @@ var Cadenza = class {
3035
3239
  maxWait: 0,
3036
3240
  isUnique: false,
3037
3241
  isMeta: false,
3242
+ isSubMeta: false,
3243
+ isHidden: false,
3038
3244
  inputSchema: void 0,
3039
3245
  validateInputContext: false,
3040
3246
  outputSchema: void 0,
@@ -3055,6 +3261,8 @@ var Cadenza = class {
3055
3261
  options.register,
3056
3262
  options.isUnique,
3057
3263
  options.isMeta,
3264
+ options.isSubMeta,
3265
+ options.isHidden,
3058
3266
  options.inputSchema,
3059
3267
  options.validateInputContext,
3060
3268
  options.outputSchema,
@@ -3079,6 +3287,8 @@ var Cadenza = class {
3079
3287
  maxWait: 0,
3080
3288
  isUnique: false,
3081
3289
  isMeta: false,
3290
+ isSubMeta: false,
3291
+ isHidden: false,
3082
3292
  inputSchema: void 0,
3083
3293
  validateInputContext: false,
3084
3294
  outputSchema: void 0,
@@ -3099,18 +3309,20 @@ var Cadenza = class {
3099
3309
  * @param name Identifier (may not be unique if not registered).
3100
3310
  * @param func Function.
3101
3311
  * @param description Optional.
3102
- * @param once Destroy after first exec (default true).
3103
- * @param destroyCondition Predicate for destruction (default always true).
3104
- * @param options Optional task options.
3312
+ * @param options Optional task options plus optional "once" (true) and "destroyCondition" (ctx => boolean).
3105
3313
  * @returns The created EphemeralTask.
3106
3314
  * @edge Destruction triggered post-exec via Node/Builder; emits meta-signal for cleanup.
3107
3315
  */
3108
- static createEphemeralTask(name, func, description, once = true, destroyCondition = () => true, options = {
3316
+ static createEphemeralTask(name, func, description, options = {
3109
3317
  concurrency: 0,
3110
3318
  timeout: 0,
3111
3319
  register: true,
3112
3320
  isUnique: false,
3113
3321
  isMeta: false,
3322
+ isSubMeta: false,
3323
+ isHidden: false,
3324
+ once: true,
3325
+ destroyCondition: () => true,
3114
3326
  getTagCallback: void 0,
3115
3327
  inputSchema: void 0,
3116
3328
  validateInputContext: false,
@@ -3127,13 +3339,15 @@ var Cadenza = class {
3127
3339
  name,
3128
3340
  func,
3129
3341
  description,
3130
- once,
3131
- destroyCondition,
3342
+ options.once,
3343
+ options.destroyCondition,
3132
3344
  options.concurrency,
3133
3345
  options.timeout,
3134
3346
  options.register,
3135
3347
  options.isUnique,
3136
3348
  options.isMeta,
3349
+ options.isSubMeta,
3350
+ options.isHidden,
3137
3351
  options.getTagCallback,
3138
3352
  options.inputSchema,
3139
3353
  options.validateInputContext,
@@ -3150,17 +3364,19 @@ var Cadenza = class {
3150
3364
  * @param name Identifier.
3151
3365
  * @param func Function.
3152
3366
  * @param description Optional.
3153
- * @param once Destroy after first (default true).
3154
- * @param destroyCondition Destruction predicate.
3155
- * @param options Optional task options.
3367
+ * @param options Optional task options plus optional "once" (true) and "destroyCondition" (ctx => boolean).
3156
3368
  * @returns The created EphemeralMetaTask.
3157
3369
  */
3158
- static createEphemeralMetaTask(name, func, description, once = true, destroyCondition = () => true, options = {
3370
+ static createEphemeralMetaTask(name, func, description, options = {
3159
3371
  concurrency: 0,
3160
3372
  timeout: 0,
3161
3373
  register: true,
3162
3374
  isUnique: false,
3163
3375
  isMeta: true,
3376
+ isSubMeta: false,
3377
+ isHidden: false,
3378
+ once: true,
3379
+ destroyCondition: () => true,
3164
3380
  getTagCallback: void 0,
3165
3381
  inputSchema: void 0,
3166
3382
  validateInputContext: false,
@@ -3172,14 +3388,7 @@ var Cadenza = class {
3172
3388
  retryDelayFactor: 1
3173
3389
  }) {
3174
3390
  options.isMeta = true;
3175
- return this.createEphemeralTask(
3176
- name,
3177
- func,
3178
- description,
3179
- once,
3180
- destroyCondition,
3181
- options
3182
- );
3391
+ return this.createEphemeralTask(name, func, description, options);
3183
3392
  }
3184
3393
  /**
3185
3394
  * Creates a GraphRoutine (named entry to starting tasks) and registers it.
@@ -3216,6 +3425,7 @@ var Cadenza = class {
3216
3425
  var _a, _b;
3217
3426
  (_a = this.broker) == null ? void 0 : _a.reset();
3218
3427
  (_b = this.registry) == null ? void 0 : _b.reset();
3428
+ this.isBootstrapped = false;
3219
3429
  }
3220
3430
  };
3221
3431
  Cadenza.isBootstrapped = false;