@anvia/core 1.0.0-rc.1 → 1.0.0-rc.3

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.
Files changed (151) hide show
  1. package/README.md +344 -85
  2. package/dist/agent/index.d.ts +33 -18
  3. package/dist/agent/index.js +42 -17
  4. package/dist/agent-CXScUOpX.d.ts +150 -0
  5. package/dist/{chunk-R2LJSQUW.js → chunk-3CMWKK32.js} +260 -104
  6. package/dist/chunk-3CMWKK32.js.map +1 -0
  7. package/dist/chunk-3RM57ZT2.js +31 -0
  8. package/dist/chunk-3RM57ZT2.js.map +1 -0
  9. package/dist/chunk-5MK3BISB.js +704 -0
  10. package/dist/chunk-5MK3BISB.js.map +1 -0
  11. package/dist/chunk-AI5JMUW7.js +45 -0
  12. package/dist/chunk-AI5JMUW7.js.map +1 -0
  13. package/dist/{chunk-FNQB2JEH.js → chunk-AZB6N7P4.js} +94 -65
  14. package/dist/chunk-AZB6N7P4.js.map +1 -0
  15. package/dist/chunk-BEYBU7VJ.js +53 -0
  16. package/dist/chunk-BEYBU7VJ.js.map +1 -0
  17. package/dist/chunk-BY4OMNIU.js +4699 -0
  18. package/dist/chunk-BY4OMNIU.js.map +1 -0
  19. package/dist/chunk-D2ECOWN5.js +515 -0
  20. package/dist/chunk-D2ECOWN5.js.map +1 -0
  21. package/dist/{chunk-A3UBYTJT.js → chunk-FN7HLLAZ.js} +60 -6
  22. package/dist/chunk-FN7HLLAZ.js.map +1 -0
  23. package/dist/chunk-GKDERULJ.js +50 -0
  24. package/dist/chunk-GKDERULJ.js.map +1 -0
  25. package/dist/chunk-GQL5KRAH.js +331 -0
  26. package/dist/chunk-GQL5KRAH.js.map +1 -0
  27. package/dist/{chunk-5XKDW36Z.js → chunk-KFR4CDGK.js} +70 -75
  28. package/dist/chunk-KFR4CDGK.js.map +1 -0
  29. package/dist/chunk-KV6QCRQ4.js +171 -0
  30. package/dist/chunk-KV6QCRQ4.js.map +1 -0
  31. package/dist/{chunk-DMPUP4R3.js → chunk-LXMAFD23.js} +5 -5
  32. package/dist/{chunk-I6G7BC42.js → chunk-MGNTXGTX.js} +2 -6
  33. package/dist/chunk-MGNTXGTX.js.map +1 -0
  34. package/dist/chunk-PK5LKOFL.js +239 -0
  35. package/dist/chunk-PK5LKOFL.js.map +1 -0
  36. package/dist/chunk-QOUPWOGW.js +29 -0
  37. package/dist/chunk-QOUPWOGW.js.map +1 -0
  38. package/dist/chunk-TRQ3XRFD.js +54 -0
  39. package/dist/chunk-TRQ3XRFD.js.map +1 -0
  40. package/dist/chunk-VKYZZXP5.js +323 -0
  41. package/dist/chunk-VKYZZXP5.js.map +1 -0
  42. package/dist/chunk-ZCPOIDAQ.js +127 -0
  43. package/dist/chunk-ZCPOIDAQ.js.map +1 -0
  44. package/dist/client-DvUatElp.d.ts +84 -0
  45. package/dist/completion/index.d.ts +5 -4
  46. package/dist/completion/index.js +25 -28
  47. package/dist/documents/index.d.ts +34 -0
  48. package/dist/documents/index.js +315 -0
  49. package/dist/documents/index.js.map +1 -0
  50. package/dist/{dynamic-tools-i9woysFa.d.ts → dynamic-tools-AEBOTgu1.d.ts} +21 -9
  51. package/dist/embeddings/index.d.ts +11 -9
  52. package/dist/embeddings/index.js +3 -3
  53. package/dist/evals/index.d.ts +53 -25
  54. package/dist/evals/index.js +153 -103
  55. package/dist/evals/index.js.map +1 -1
  56. package/dist/extractor/index.d.ts +23 -26
  57. package/dist/extractor/index.js +7 -8
  58. package/dist/guardrails/index.d.ts +7 -129
  59. package/dist/guardrails/index.js +1 -1
  60. package/dist/image-generation/index.d.ts +18 -16
  61. package/dist/image-generation/index.js +2 -2
  62. package/dist/index.d.ts +26 -23
  63. package/dist/index.js +71 -48
  64. package/dist/interactions-csssHYcN.d.ts +174 -0
  65. package/dist/internal/agent.d.ts +36 -29
  66. package/dist/internal/agent.js +48 -15
  67. package/dist/internal/agent.js.map +1 -1
  68. package/dist/mcp/index.d.ts +19 -13
  69. package/dist/mcp/index.js +14 -348
  70. package/dist/mcp/index.js.map +1 -1
  71. package/dist/memory/index.d.ts +20 -6
  72. package/dist/memory/index.js +10 -10
  73. package/dist/message-schema-B2M7AYzR.d.ts +52 -0
  74. package/dist/model-call-options-CZkSw_xN.d.ts +6 -0
  75. package/dist/model-listing/index.d.ts +3 -1
  76. package/dist/observability/index.d.ts +21 -6
  77. package/dist/observability/index.js +8 -5
  78. package/dist/observability/index.js.map +1 -1
  79. package/dist/pipeline/index.d.ts +106 -57
  80. package/dist/pipeline/index.js +419 -236
  81. package/dist/pipeline/index.js.map +1 -1
  82. package/dist/{retry-D3Ruy-ba.d.ts → retry-CjvSlKGW.d.ts} +2 -1
  83. package/dist/skills/index.d.ts +5 -4
  84. package/dist/skills/index.js +8 -7
  85. package/dist/speech-generation/index.d.ts +37 -0
  86. package/dist/speech-generation/index.js +8 -0
  87. package/dist/text-C_6eKrbC.d.ts +32 -0
  88. package/dist/{think-tool-DZqZj2LV.d.ts → think-tool-D8frXxwV.d.ts} +16 -2
  89. package/dist/tool/index.d.ts +9 -7
  90. package/dist/tool/index.js +12 -10
  91. package/dist/{tool-C_8GudXn.d.ts → tool-r62gf3QY.d.ts} +17 -8
  92. package/dist/transcription/index.d.ts +23 -14
  93. package/dist/transcription/index.js +2 -2
  94. package/dist/types-C3gv9EX6.d.ts +130 -0
  95. package/dist/{index-DxB74ybJ.d.ts → types-CElwurHZ.d.ts} +139 -88
  96. package/dist/types-CIPaIbZo.d.ts +105 -0
  97. package/dist/types-Cr4uiYo5.d.ts +99 -0
  98. package/dist/types-D9rKQ_as.d.ts +341 -0
  99. package/dist/types-DbolvLtZ.d.ts +155 -0
  100. package/dist/{types-DhQfwiZn.d.ts → types-RT3cuyRk.d.ts} +1 -1
  101. package/dist/vector-store/index.d.ts +33 -34
  102. package/dist/vector-store/index.js +7 -6
  103. package/package.json +10 -14
  104. package/dist/agent-DGYY_onS.d.ts +0 -145
  105. package/dist/audio-generation/index.d.ts +0 -31
  106. package/dist/audio-generation/index.js +0 -8
  107. package/dist/chunk-5XKDW36Z.js.map +0 -1
  108. package/dist/chunk-6WGGTJE6.js +0 -139
  109. package/dist/chunk-6WGGTJE6.js.map +0 -1
  110. package/dist/chunk-A3UBYTJT.js.map +0 -1
  111. package/dist/chunk-ADH7NNCS.js +0 -512
  112. package/dist/chunk-ADH7NNCS.js.map +0 -1
  113. package/dist/chunk-DZ3CKYTH.js +0 -267
  114. package/dist/chunk-DZ3CKYTH.js.map +0 -1
  115. package/dist/chunk-FNQB2JEH.js.map +0 -1
  116. package/dist/chunk-I6G7BC42.js.map +0 -1
  117. package/dist/chunk-IL3ZSNJI.js +0 -3748
  118. package/dist/chunk-IL3ZSNJI.js.map +0 -1
  119. package/dist/chunk-J6GNQART.js +0 -122
  120. package/dist/chunk-J6GNQART.js.map +0 -1
  121. package/dist/chunk-M3IOWB4Y.js +0 -280
  122. package/dist/chunk-M3IOWB4Y.js.map +0 -1
  123. package/dist/chunk-QY5GZ7HR.js +0 -39
  124. package/dist/chunk-QY5GZ7HR.js.map +0 -1
  125. package/dist/chunk-R2LJSQUW.js.map +0 -1
  126. package/dist/chunk-RFDVKCIE.js +0 -12
  127. package/dist/chunk-RFDVKCIE.js.map +0 -1
  128. package/dist/chunk-RMUBRRSK.js +0 -34
  129. package/dist/chunk-RMUBRRSK.js.map +0 -1
  130. package/dist/chunk-RXKHOYEH.js +0 -466
  131. package/dist/chunk-RXKHOYEH.js.map +0 -1
  132. package/dist/chunk-XDRSPSR7.js +0 -38
  133. package/dist/chunk-XDRSPSR7.js.map +0 -1
  134. package/dist/chunk-XWUC7CIT.js +0 -1
  135. package/dist/chunk-XWUC7CIT.js.map +0 -1
  136. package/dist/errors-CYKUcU89.d.ts +0 -17
  137. package/dist/json-Zo7K3xmt.d.ts +0 -40
  138. package/dist/loaders/index.d.ts +0 -86
  139. package/dist/loaders/index.js +0 -299
  140. package/dist/loaders/index.js.map +0 -1
  141. package/dist/middleware-KynLg_RW.d.ts +0 -56
  142. package/dist/types-B3A4YxaA.d.ts +0 -354
  143. package/dist/types-BBEGKB9m.d.ts +0 -119
  144. package/dist/types-DT3nEemY.d.ts +0 -79
  145. package/dist/types-DulRCYdB.d.ts +0 -70
  146. package/dist/types-p55Jc-sr.d.ts +0 -47
  147. package/dist/ui/index.d.ts +0 -107
  148. package/dist/ui/index.js +0 -10
  149. package/dist/ui/index.js.map +0 -1
  150. /package/dist/{chunk-DMPUP4R3.js.map → chunk-LXMAFD23.js.map} +0 -0
  151. /package/dist/{audio-generation → speech-generation}/index.js.map +0 -0
@@ -1,195 +1,296 @@
1
1
  import {
2
- cancelAgentApproval
3
- } from "../chunk-IL3ZSNJI.js";
4
- import "../chunk-YK4WAAS4.js";
5
- import "../chunk-6WGGTJE6.js";
6
- import "../chunk-R2LJSQUW.js";
7
- import "../chunk-5XKDW36Z.js";
2
+ AgentRunBlockedError
3
+ } from "../chunk-TRQ3XRFD.js";
8
4
  import {
9
5
  mapWithConcurrency
10
- } from "../chunk-DZ3CKYTH.js";
11
- import "../chunk-I6G7BC42.js";
12
- import "../chunk-M3IOWB4Y.js";
13
- import "../chunk-RFDVKCIE.js";
14
- import "../chunk-ADH7NNCS.js";
15
- import "../chunk-A3UBYTJT.js";
16
- import "../chunk-FNQB2JEH.js";
6
+ } from "../chunk-3RM57ZT2.js";
7
+ import {
8
+ extract
9
+ } from "../chunk-ZCPOIDAQ.js";
10
+ import "../chunk-MGNTXGTX.js";
11
+ import "../chunk-D2ECOWN5.js";
12
+ import "../chunk-PK5LKOFL.js";
13
+ import {
14
+ abortError,
15
+ throwIfAborted
16
+ } from "../chunk-FN7HLLAZ.js";
17
+
18
+ // src/pipeline/errors.ts
19
+ var PipelineAgentSuspensionError = class extends Error {
20
+ constructor(result) {
21
+ super("Pipeline agent stage suspended for human interaction.");
22
+ this.result = result;
23
+ this.name = "PipelineAgentSuspensionError";
24
+ }
25
+ result;
26
+ };
17
27
 
18
28
  // src/pipeline/pipeline.ts
19
29
  import { z } from "zod";
20
30
 
21
31
  // src/pipeline/graph.ts
22
- function initialPipelineState(metadata) {
23
- return {
24
- graph: initialGraph(metadata),
25
- terminalNodeId: "input",
26
- terminalNodeIds: ["input"],
27
- nextNodeIndex: 1,
28
- nextEdgeIndex: 1
29
- };
30
- }
31
- function initialGraph(metadata) {
32
- const id = metadata.id ?? "pipeline";
32
+ var INPUT_ID = "$input";
33
+ var OUTPUT_ID = "$output";
34
+ var RESERVED_STAGE_IDS = /* @__PURE__ */ new Set([INPUT_ID, OUTPUT_ID]);
35
+ function initialPipelineState(options) {
36
+ const input = graphNode(INPUT_ID, [INPUT_ID], "input", "Input");
33
37
  const graph = {
34
- id,
35
- nodes: [{ id: "input", kind: "input", label: "Input" }],
38
+ id: options.id,
39
+ nodes: [input],
36
40
  edges: []
37
41
  };
38
- if (metadata.name !== void 0) {
39
- graph.name = metadata.name;
40
- }
41
- if (metadata.description !== void 0) {
42
- graph.description = metadata.description;
43
- }
44
- if (metadata.metadata !== void 0) {
45
- graph.metadata = metadata.metadata;
46
- }
47
- return graph;
48
- }
49
- function appendNode(state, kind, label, options = {}) {
50
- const node = graphNode(kind, label, state.nextNodeIndex, {
51
- ...options,
52
- existingIds: new Set(state.graph.nodes.map((item) => item.id))
53
- });
42
+ if (options.name !== void 0) graph.name = options.name;
43
+ if (options.description !== void 0) graph.description = options.description;
44
+ if (options.metadata !== void 0) graph.metadata = options.metadata;
54
45
  return {
55
- node,
56
- state: appendGraphNode(state, node, activeTerminalNodeIds(state), [node.id])
46
+ graph,
47
+ terminalPaths: [input.path],
48
+ stageIds: /* @__PURE__ */ new Set(),
49
+ nextEdgeIndex: 1
57
50
  };
58
51
  }
59
- function appendChildNode(state, parentId, kind, label, options = {}) {
60
- const node = graphNode(kind, label, state.nextNodeIndex, {
61
- ...options,
62
- existingIds: new Set(state.graph.nodes.map((item) => item.id))
52
+ function appendStageNode(state, kind, stage, options = {}) {
53
+ const id = validateStageId(stage.id);
54
+ if (state.stageIds.has(id)) {
55
+ throw new TypeError(`Pipeline stage id "${id}" is already registered.`);
56
+ }
57
+ const node = graphNode(id, [id], kind, stage.name ?? options.defaultLabel ?? id, {
58
+ description: stage.description,
59
+ metadata: stage.metadata,
60
+ agentId: options.agentId,
61
+ agentName: options.agentName,
62
+ pipelineId: options.pipelineId
63
63
  });
64
64
  return {
65
65
  node,
66
- state: appendGraphNode(state, node, [parentId], activeTerminalNodeIds(state))
66
+ state: appendNode(state, node, state.terminalPaths, [node.path], id)
67
67
  };
68
68
  }
69
- function activeTerminalNodeIds(state) {
70
- return state.terminalNodeIds.length > 0 ? state.terminalNodeIds : [state.terminalNodeId];
69
+ function appendComposedGraph(state, boundary, child) {
70
+ return appendChildGraph(state, boundary.path, child);
71
71
  }
72
- function withTerminalNodes(state, terminalNodeIds) {
73
- return {
74
- ...state,
75
- terminalNodeId: terminalNodeIds.at(-1) ?? state.terminalNodeId,
76
- terminalNodeIds
77
- };
72
+ function appendParallelBranch(state, parallel, branchKey, child) {
73
+ const id = validateStageId(branchKey);
74
+ const path = [...parallel.path, id];
75
+ const node = graphNode(id, path, "branch", id, { branchKey: id, pipelineId: child.id });
76
+ const withBranch = appendNode(state, node, [parallel.path], state.terminalPaths);
77
+ const withChild = appendChildGraph(withBranch, node.path, child);
78
+ return { state: withChild, node, terminalPaths: withChild.terminalPaths };
79
+ }
80
+ function withTerminalPaths(state, terminalPaths) {
81
+ return { ...state, terminalPaths };
78
82
  }
79
83
  function withOutputNode(state) {
80
84
  const graph = cloneGraph(state.graph);
81
- if (graph.nodes.some((node) => node.id === "output")) {
85
+ const outputPath = [OUTPUT_ID];
86
+ if (graph.nodes.some((node) => pathEquals(node.path, outputPath))) {
82
87
  return graph;
83
88
  }
84
- graph.nodes.push({ id: "output", kind: "output", label: "Output" });
89
+ graph.nodes.push(graphNode(OUTPUT_ID, outputPath, "output", "Output"));
85
90
  graph.edges.push(
86
- ...activeTerminalNodeIds(state).map((sourceId, index) => ({
91
+ ...state.terminalPaths.map((source, index) => ({
87
92
  id: `edge_${state.nextEdgeIndex + index}`,
88
- source: sourceId,
89
- target: "output"
93
+ source: [...source],
94
+ target: outputPath
90
95
  }))
91
96
  );
92
97
  return graph;
93
98
  }
94
- function nextStageLabel(state, prefix) {
95
- return `${prefix} ${state.nextNodeIndex}`;
96
- }
97
99
  function cloneGraph(graph) {
98
100
  return {
99
101
  ...graph,
100
- nodes: graph.nodes.map((node) => ({ ...node })),
101
- edges: graph.edges.map((edge) => ({ ...edge }))
102
+ nodes: graph.nodes.map((node) => ({ ...node, path: [...node.path] })),
103
+ edges: graph.edges.map((edge) => ({
104
+ ...edge,
105
+ source: [...edge.source],
106
+ target: [...edge.target]
107
+ }))
102
108
  };
103
109
  }
104
- function appendGraphNode(state, node, sourceIds, terminalNodeIds) {
105
- const edges = sourceIds.map((sourceId, index) => ({
110
+ function scopedNode(node, path) {
111
+ return { ...node, path: [...path] };
112
+ }
113
+ function appendChildGraph(state, parentPath, child) {
114
+ const childNodes = child.nodes.filter((node) => !isBoundaryPath(node.path)).map((node) => scopedNode(node, [...parentPath, ...node.path]));
115
+ const childEdges = [];
116
+ const terminalPaths = [];
117
+ let nextEdgeIndex = state.nextEdgeIndex;
118
+ for (const edge of child.edges) {
119
+ const sourceIsInput = isInputPath(edge.source);
120
+ const targetIsOutput = isOutputPath(edge.target);
121
+ const source = sourceIsInput ? [...parentPath] : [...parentPath, ...edge.source];
122
+ if (targetIsOutput) {
123
+ terminalPaths.push(source);
124
+ continue;
125
+ }
126
+ const target = [...parentPath, ...edge.target];
127
+ let childEdge = {
128
+ id: `edge_${nextEdgeIndex}`,
129
+ source,
130
+ target
131
+ };
132
+ if (edge.label !== void 0) childEdge = { ...childEdge, label: edge.label };
133
+ childEdges.push(childEdge);
134
+ nextEdgeIndex += 1;
135
+ }
136
+ return {
137
+ ...state,
138
+ graph: {
139
+ ...state.graph,
140
+ nodes: [...state.graph.nodes, ...childNodes],
141
+ edges: [...state.graph.edges, ...childEdges]
142
+ },
143
+ terminalPaths: terminalPaths.length === 0 ? [[...parentPath]] : terminalPaths,
144
+ nextEdgeIndex
145
+ };
146
+ }
147
+ function appendNode(state, node, sourcePaths, terminalPaths, stageId) {
148
+ const edges = sourcePaths.map((source, index) => ({
106
149
  id: `edge_${state.nextEdgeIndex + index}`,
107
- source: sourceId,
108
- target: node.id
150
+ source: [...source],
151
+ target: [...node.path]
109
152
  }));
110
- const terminalNodeId = terminalNodeIds.at(-1) ?? state.terminalNodeId;
153
+ const stageIds = new Set(state.stageIds);
154
+ if (stageId !== void 0) stageIds.add(stageId);
111
155
  return {
112
156
  graph: {
113
157
  ...state.graph,
114
158
  nodes: [...state.graph.nodes, node],
115
159
  edges: [...state.graph.edges, ...edges]
116
160
  },
117
- terminalNodeId,
118
- terminalNodeIds,
119
- nextNodeIndex: state.nextNodeIndex + 1,
161
+ terminalPaths,
162
+ stageIds,
120
163
  nextEdgeIndex: state.nextEdgeIndex + edges.length
121
164
  };
122
165
  }
123
- function graphNode(kind, label, index, options = {}) {
124
- const id = uniqueGraphNodeId(
125
- normalizeId(options.preferredId ?? `${kind}_${index}`),
126
- options.existingIds ?? /* @__PURE__ */ new Set()
127
- );
128
- const node = {
129
- id,
130
- kind,
131
- label
132
- };
133
- if (options.description !== void 0) {
134
- node.description = options.description;
135
- }
136
- if (options.metadata !== void 0) {
137
- node.metadata = options.metadata;
138
- }
139
- if (options.agentId !== void 0) {
140
- node.agentId = options.agentId;
141
- }
142
- if (options.agentName !== void 0) {
143
- node.agentName = options.agentName;
166
+ function graphNode(id, path, kind, label, options = {}) {
167
+ const node = { id, path: [...path], kind, label };
168
+ if (options.description !== void 0) node.description = options.description;
169
+ if (options.metadata !== void 0) node.metadata = options.metadata;
170
+ if (options.agentId !== void 0) node.agentId = options.agentId;
171
+ if (options.agentName !== void 0) node.agentName = options.agentName;
172
+ if (options.pipelineId !== void 0) node.pipelineId = options.pipelineId;
173
+ if (options.branchKey !== void 0) node.branchKey = options.branchKey;
174
+ return node;
175
+ }
176
+ function validateStageId(value) {
177
+ if (typeof value !== "string") {
178
+ throw new TypeError("Pipeline stage id must be a string.");
144
179
  }
145
- if (options.pipelineId !== void 0) {
146
- node.pipelineId = options.pipelineId;
180
+ const id = value.trim();
181
+ if (id.length === 0) {
182
+ throw new TypeError("Pipeline stage id must be a non-empty string.");
147
183
  }
148
- if (options.branchKey !== void 0) {
149
- node.branchKey = options.branchKey;
184
+ if (RESERVED_STAGE_IDS.has(id)) {
185
+ throw new TypeError(`Pipeline stage id "${id}" is reserved.`);
150
186
  }
151
- return node;
187
+ return id;
152
188
  }
153
- function normalizeId(value) {
154
- const normalized = value.trim().toLowerCase().replace(/[^a-z0-9_-]+/g, "_").replace(/^_+|_+$/g, "");
155
- return normalized.length === 0 ? "pipeline" : normalized;
189
+ function isBoundaryPath(path) {
190
+ return isInputPath(path) || isOutputPath(path);
156
191
  }
157
- function uniqueGraphNodeId(baseId, existingIds) {
158
- let id = baseId;
159
- let suffix = 2;
160
- while (existingIds.has(id)) {
161
- id = `${baseId}_${suffix}`;
162
- suffix += 1;
163
- }
164
- return id;
192
+ function isInputPath(path) {
193
+ return path.length === 1 && path[0] === INPUT_ID;
194
+ }
195
+ function isOutputPath(path) {
196
+ return path.length === 1 && path[0] === OUTPUT_ID;
197
+ }
198
+ function pathEquals(left, right) {
199
+ return left.length === right.length && left.every((segment, index) => segment === right[index]);
165
200
  }
166
201
 
167
202
  // src/pipeline/runtime.ts
168
- async function runNode(context, node, fn) {
203
+ async function runNode(context, node, path, fn) {
204
+ throwIfAborted(context.abortSignal);
205
+ const eventNode = scopedNode(node, path);
169
206
  const startedAt = Date.now();
170
- await context.observer?.onEvent({ type: "stage_started", node });
207
+ await emitEvent(context, {
208
+ type: "stage_started",
209
+ runId: context.runId,
210
+ pipelineId: context.pipelineId,
211
+ path: [...path],
212
+ node: eventNode
213
+ });
171
214
  try {
172
215
  const output = await fn();
173
- await context.observer?.onEvent({
216
+ throwIfAborted(context.abortSignal);
217
+ await emitEvent(context, {
174
218
  type: "stage_completed",
175
- node,
219
+ runId: context.runId,
220
+ pipelineId: context.pipelineId,
221
+ path: [...path],
222
+ node: eventNode,
176
223
  durationMs: Date.now() - startedAt
177
224
  });
178
225
  return output;
179
226
  } catch (error) {
180
- await context.observer?.onEvent({
227
+ const failureEvent = {
181
228
  type: "stage_failed",
182
- node,
229
+ runId: context.runId,
230
+ pipelineId: context.pipelineId,
231
+ path: [...path],
232
+ node: eventNode,
183
233
  durationMs: Date.now() - startedAt,
184
234
  error
185
- });
235
+ };
236
+ try {
237
+ await emitEvent(context, failureEvent);
238
+ } catch (observerError) {
239
+ throw new AggregateError(
240
+ [error, observerError],
241
+ `Pipeline stage "${node.id}" and its observer both failed.`
242
+ );
243
+ }
186
244
  throw error;
187
245
  }
188
246
  }
247
+ function stageContext(input, context) {
248
+ return {
249
+ input,
250
+ runId: context.runId,
251
+ pipelineId: context.pipelineId,
252
+ runMetadata: context.runMetadata,
253
+ abortSignal: context.abortSignal
254
+ };
255
+ }
256
+ function childContext(context, abortSignal) {
257
+ return { ...context, abortSignal };
258
+ }
259
+ function combineAbortSignals(parent, local) {
260
+ const controller = new AbortController();
261
+ const abortFromParent = () => controller.abort(parent?.reason);
262
+ const abortFromLocal = () => controller.abort(local.reason);
263
+ if (parent?.aborted === true) {
264
+ controller.abort(parent.reason);
265
+ } else if (local.aborted) {
266
+ controller.abort(local.reason);
267
+ } else {
268
+ parent?.addEventListener("abort", abortFromParent, { once: true });
269
+ local.addEventListener("abort", abortFromLocal, { once: true });
270
+ }
271
+ return {
272
+ signal: controller.signal,
273
+ dispose() {
274
+ parent?.removeEventListener("abort", abortFromParent);
275
+ local.removeEventListener("abort", abortFromLocal);
276
+ }
277
+ };
278
+ }
279
+ function pipelineAbortError(signal) {
280
+ return abortError(signal?.reason);
281
+ }
282
+ async function emitEvent(context, event) {
283
+ if (context.observer === void 0) return;
284
+ try {
285
+ await context.observer.onEvent(event);
286
+ } catch (error) {
287
+ if (context.failOnObserverError) throw error;
288
+ }
289
+ }
189
290
 
190
291
  // src/pipeline/pipeline.ts
191
292
  var internalPipelineOptions = /* @__PURE__ */ Symbol("internal-pipeline-options");
192
- var Pipeline = class _Pipeline {
293
+ var Pipeline = class {
193
294
  id;
194
295
  name;
195
296
  description;
@@ -206,7 +307,10 @@ var Pipeline = class _Pipeline {
206
307
  throw new TypeError("Pipeline inputSchema must be a Zod schema.");
207
308
  }
208
309
  const inputSchema = options.inputSchema;
209
- this.executor = ((input) => inputSchema.parse(input));
310
+ this.executor = (async (input, context) => {
311
+ throwIfAborted(context.abortSignal);
312
+ return inputSchema.parseAsync(input);
313
+ });
210
314
  this.state = initialPipelineState({
211
315
  id,
212
316
  name: options.name,
@@ -220,143 +324,191 @@ var Pipeline = class _Pipeline {
220
324
  this.description = graph.description;
221
325
  this.metadata = graph.metadata;
222
326
  }
223
- /** Add a synchronous or asynchronous transform stage. */
224
- step(fn, metadata) {
225
- const next = appendNode(
226
- this.state,
227
- "step",
228
- metadata?.name ?? nextStageLabel(this.state, "Step"),
229
- {
230
- description: metadata?.description,
231
- metadata: metadata?.metadata,
232
- preferredId: metadata?.id
233
- }
234
- );
235
- return this.derive(async (input, context) => {
236
- const value = await this.runStep(input, context);
237
- const result = await runNode(context, next.node, () => fn(value));
238
- return result;
239
- }, next.state);
327
+ step(options) {
328
+ const next = appendStageNode(this.state, "step", options);
329
+ const executor = (async (input, context, pathPrefix) => {
330
+ const value = await this.execute(input, context, pathPrefix);
331
+ const path = [...pathPrefix, next.node.id];
332
+ return await runNode(
333
+ context,
334
+ next.node,
335
+ path,
336
+ () => options.run(stageContext(value, context))
337
+ );
338
+ });
339
+ return this.derive(executor, next.state);
240
340
  }
241
- /** Compose another pipeline operation after the current stage. */
242
- use(op, metadata) {
243
- const nested = op instanceof _Pipeline ? op : void 0;
244
- const next = appendNode(
245
- this.state,
246
- nested === void 0 ? "step" : "pipeline",
247
- metadata?.name ?? nested?.name ?? nested?.id ?? nextStageLabel(this.state, nested === void 0 ? "Operation" : "Pipeline"),
248
- {
249
- description: metadata?.description ?? nested?.description,
250
- metadata: metadata?.metadata ?? nested?.metadata,
251
- preferredId: metadata?.id,
252
- pipelineId: nested?.id
253
- }
254
- );
255
- return this.derive(async (input, context) => {
256
- const value = await this.runStep(input, context);
257
- const result = await runNode(context, next.node, () => op.run(value));
258
- return result;
259
- }, next.state);
341
+ compose(options) {
342
+ const boundary = appendStageNode(this.state, "pipeline", options, {
343
+ defaultLabel: options.pipeline.name ?? options.pipeline.id,
344
+ pipelineId: options.pipeline.id
345
+ });
346
+ const state = appendComposedGraph(boundary.state, boundary.node, options.pipeline.graph());
347
+ const executor = (async (input, context, pathPrefix) => {
348
+ const value = await this.execute(input, context, pathPrefix);
349
+ const path = [...pathPrefix, boundary.node.id];
350
+ return await runNode(
351
+ context,
352
+ boundary.node,
353
+ path,
354
+ () => options.pipeline.execute(value, context, path)
355
+ );
356
+ });
357
+ return this.derive(executor, state);
260
358
  }
261
- /** Run named branch operations concurrently from the current value. */
262
- parallel(branches, metadata) {
263
- const parallel = appendNode(
264
- this.state,
265
- "parallel",
266
- metadata?.name ?? `${Object.keys(branches).length} parallel branches`,
267
- {
268
- description: metadata?.description,
269
- metadata: metadata?.metadata,
270
- preferredId: metadata?.id
271
- }
272
- );
359
+ parallel(options) {
360
+ const branchEntries = normalizeParallelBranches(options.branches);
361
+ if (branchEntries.length === 0) {
362
+ throw new TypeError("Pipeline parallel branches must not be empty.");
363
+ }
364
+ const parallel = appendStageNode(this.state, "parallel", options, {
365
+ defaultLabel: `${branchEntries.length} parallel branches`
366
+ });
273
367
  let nextState = parallel.state;
274
- const branchNodes = {};
275
- for (const key of Object.keys(branches)) {
276
- const branch = appendChildNode(nextState, parallel.node.id, "branch", key, {
277
- branchKey: key
278
- });
279
- nextState = branch.state;
280
- branchNodes[key] = branch.node;
368
+ const branchNodes = /* @__PURE__ */ new Map();
369
+ const terminalPaths = [];
370
+ for (const [key, branch] of branchEntries) {
371
+ const appended = appendParallelBranch(nextState, parallel.node, key, branch.graph());
372
+ nextState = appended.state;
373
+ branchNodes.set(key, appended.node);
374
+ terminalPaths.push(...appended.terminalPaths);
281
375
  }
282
- nextState = withTerminalNodes(
283
- nextState,
284
- Object.values(branchNodes).map((node) => node.id)
285
- );
286
- return this.derive(async (input, context) => {
287
- const value = await this.runStep(input, context);
288
- const entries = await runNode(
289
- context,
290
- parallel.node,
291
- () => Promise.all(
292
- Object.entries(branches).map(async ([key, op]) => {
293
- const node = branchNodes[key];
294
- const output = await runNode(context, node, () => op.run(value));
376
+ nextState = withTerminalPaths(nextState, terminalPaths);
377
+ return this.derive(async (input, context, pathPrefix) => {
378
+ const value = await this.execute(input, context, pathPrefix);
379
+ const parallelPath = [...pathPrefix, parallel.node.id];
380
+ return runNode(context, parallel.node, parallelPath, async () => {
381
+ const controller = new AbortController();
382
+ const combined = combineAbortSignals(context.abortSignal, controller.signal);
383
+ const branchContext = childContext(context, combined.signal);
384
+ let firstError;
385
+ const promises = branchEntries.map(async ([key, branch]) => {
386
+ const node = branchNodes.get(key);
387
+ const path = [...parallelPath, node.id];
388
+ try {
389
+ const output = await runNode(
390
+ branchContext,
391
+ node,
392
+ path,
393
+ () => branch.execute(value, branchContext, path)
394
+ );
295
395
  return [key, output];
296
- })
297
- )
298
- );
299
- return Object.fromEntries(entries);
396
+ } catch (error) {
397
+ if (firstError === void 0) firstError = error;
398
+ if (!controller.signal.aborted) controller.abort(error);
399
+ throw error;
400
+ }
401
+ });
402
+ const settled = await Promise.allSettled(promises);
403
+ combined.dispose();
404
+ if (context.abortSignal?.aborted === true) {
405
+ throw pipelineAbortError(context.abortSignal);
406
+ }
407
+ if (firstError !== void 0) throw firstError;
408
+ return Object.fromEntries(
409
+ settled.map(
410
+ (result) => result.value
411
+ )
412
+ );
413
+ });
300
414
  }, nextState);
301
415
  }
302
- /** Send the current value to an agent as text and continue with the agent output. */
303
- agent(agent, metadata) {
304
- const next = appendNode(this.state, "agent", metadata?.name ?? agent.name ?? agent.id, {
305
- description: metadata?.description ?? agent.description,
306
- metadata: metadata?.metadata,
307
- preferredId: metadata?.id,
308
- agentId: agent.id,
309
- agentName: agent.name
416
+ agent(options) {
417
+ if (options.suspension !== "reject") {
418
+ throw new TypeError('Pipeline Agent stages require suspension: "reject".');
419
+ }
420
+ const next = appendStageNode(this.state, "agent", options, {
421
+ defaultLabel: options.agent.name ?? options.agent.id,
422
+ agentId: options.agent.id,
423
+ agentName: options.agent.name
310
424
  });
311
- return this.derive(async (input, context) => {
312
- const value = await this.runStep(input, context);
313
- return runNode(context, next.node, async () => {
314
- const response = await agent.generate(String(value));
315
- if (response.status === "approval_required") {
316
- await cancelAgentApproval(
317
- response,
318
- "Pipeline agent stages cannot suspend for tool approval."
319
- );
320
- throw new Error("Pipeline agent stages cannot suspend for tool approval.");
425
+ return this.derive(async (input, context, pathPrefix) => {
426
+ const value = await this.execute(input, context, pathPrefix);
427
+ const path = [...pathPrefix, next.node.id];
428
+ return runNode(context, next.node, path, async () => {
429
+ const request = await options.request(stageContext(value, context));
430
+ const response = await options.agent.generate({
431
+ ...request,
432
+ abortSignal: context.abortSignal
433
+ });
434
+ if (response.status === "suspended") {
435
+ throw new PipelineAgentSuspensionError(response);
436
+ }
437
+ if (response.status === "blocked") {
438
+ throw new AgentRunBlockedError(response);
321
439
  }
322
440
  return response.output;
323
441
  });
324
442
  }, next.state);
325
443
  }
326
- /** Send the current value to an extractor as text and continue with typed schema data. */
327
- extract(extractor, metadata) {
328
- const next = appendNode(
329
- this.state,
330
- "extractor",
331
- metadata?.name ?? nextStageLabel(this.state, "Extractor"),
332
- {
333
- description: metadata?.description,
334
- metadata: metadata?.metadata,
335
- preferredId: metadata?.id
336
- }
337
- );
338
- return this.derive(async (input, context) => {
339
- const value = await this.runStep(input, context);
340
- return runNode(context, next.node, () => extractor.extract(String(value)));
444
+ extract(options) {
445
+ const next = appendStageNode(this.state, "extractor", options);
446
+ return this.derive(async (input, context, pathPrefix) => {
447
+ const value = await this.execute(input, context, pathPrefix);
448
+ const path = [...pathPrefix, next.node.id];
449
+ return runNode(context, next.node, path, async () => {
450
+ const text = await options.text(stageContext(value, context));
451
+ const result = await extract({
452
+ model: options.model,
453
+ text,
454
+ outputSchema: options.outputSchema,
455
+ instructions: options.instructions,
456
+ retries: options.retries,
457
+ temperature: options.temperature,
458
+ maxTokens: options.maxTokens,
459
+ providerOptions: options.providerOptions,
460
+ abortSignal: context.abortSignal
461
+ });
462
+ return result.output;
463
+ });
341
464
  }, next.state);
342
465
  }
343
- /** Run one input through the pipeline and return the final stage output. */
344
- async run(input, options = {}) {
345
- return this.runStep(input, { observer: options.observer });
466
+ async run(options) {
467
+ const runId = normalizeRunId(options.runId ?? globalThis.crypto.randomUUID());
468
+ const context = {
469
+ runId,
470
+ pipelineId: this.id,
471
+ runMetadata: options.metadata,
472
+ abortSignal: options.abortSignal,
473
+ observer: options.observer,
474
+ failOnObserverError: options.failOnObserverError === true
475
+ };
476
+ throwIfAborted(context.abortSignal);
477
+ const output = await this.execute(options.input, context, []);
478
+ throwIfAborted(context.abortSignal);
479
+ return { runId, output };
346
480
  }
347
- /** Run many inputs through the same pipeline with bounded concurrency. */
348
- async batch(inputs, options) {
349
- return mapWithConcurrency([...inputs], options.concurrency, (input) => this.run(input));
481
+ async runBatch(options) {
482
+ throwIfAborted(options.abortSignal);
483
+ return mapWithConcurrency([...options.inputs], options.concurrency, async (input) => {
484
+ const runId = globalThis.crypto.randomUUID();
485
+ try {
486
+ const result = await this.run({
487
+ input,
488
+ runId,
489
+ metadata: options.metadata,
490
+ abortSignal: options.abortSignal,
491
+ observer: options.observer,
492
+ failOnObserverError: options.failOnObserverError
493
+ });
494
+ return { status: "completed", ...result };
495
+ } catch (error) {
496
+ if (options.abortSignal?.aborted === true) {
497
+ throw pipelineAbortError(options.abortSignal);
498
+ }
499
+ return { status: "failed", runId, error };
500
+ }
501
+ });
350
502
  }
351
- /** Return an isolated graph snapshot for the current pipeline stages. */
352
503
  graph() {
353
504
  return cloneGraph(withOutputNode(this.state));
354
505
  }
355
506
  derive(executor, state) {
356
507
  return createDerivedPipeline(executor, state);
357
508
  }
358
- async runStep(input, context) {
359
- return await this.executor(input, context);
509
+ async execute(input, context, pathPrefix) {
510
+ throwIfAborted(context.abortSignal);
511
+ return await this.executor(input, context, pathPrefix);
360
512
  }
361
513
  };
362
514
  function createDerivedPipeline(executor, state) {
@@ -381,7 +533,38 @@ function normalizePipelineId(id) {
381
533
  }
382
534
  return normalized;
383
535
  }
536
+ function normalizeRunId(runId) {
537
+ if (typeof runId !== "string") {
538
+ throw new TypeError("Pipeline runId must be a string.");
539
+ }
540
+ const normalized = runId.trim();
541
+ if (normalized.length === 0) {
542
+ throw new TypeError("Pipeline runId must be a non-empty string.");
543
+ }
544
+ return normalized;
545
+ }
546
+ function normalizeParallelBranches(branches) {
547
+ const entries = [];
548
+ const ids = /* @__PURE__ */ new Set();
549
+ for (const key of Object.keys(branches)) {
550
+ const pipeline = branches[key];
551
+ const id = key.trim();
552
+ if (id.length === 0) {
553
+ throw new TypeError("Pipeline parallel branch id must be a non-empty string.");
554
+ }
555
+ if (ids.has(id)) {
556
+ throw new TypeError(`Pipeline parallel branch id "${id}" is already registered.`);
557
+ }
558
+ ids.add(id);
559
+ if (id !== key) {
560
+ throw new TypeError("Pipeline parallel branch ids must not contain surrounding whitespace.");
561
+ }
562
+ entries.push([id, pipeline]);
563
+ }
564
+ return entries;
565
+ }
384
566
  export {
385
- Pipeline
567
+ Pipeline,
568
+ PipelineAgentSuspensionError
386
569
  };
387
570
  //# sourceMappingURL=index.js.map