@inkeep/agents-run-api 0.0.0-dev-20250910232631

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 (152) hide show
  1. package/LICENSE.md +49 -0
  2. package/README.md +117 -0
  3. package/dist/__tests__/setup.d.ts +4 -0
  4. package/dist/__tests__/setup.d.ts.map +1 -0
  5. package/dist/__tests__/setup.js +80 -0
  6. package/dist/__tests__/utils/testProject.d.ts +18 -0
  7. package/dist/__tests__/utils/testProject.d.ts.map +1 -0
  8. package/dist/__tests__/utils/testProject.js +26 -0
  9. package/dist/__tests__/utils/testRequest.d.ts +8 -0
  10. package/dist/__tests__/utils/testRequest.d.ts.map +1 -0
  11. package/dist/__tests__/utils/testRequest.js +32 -0
  12. package/dist/__tests__/utils/testTenant.d.ts +64 -0
  13. package/dist/__tests__/utils/testTenant.d.ts.map +1 -0
  14. package/dist/__tests__/utils/testTenant.js +71 -0
  15. package/dist/a2a/client.d.ts +182 -0
  16. package/dist/a2a/client.d.ts.map +1 -0
  17. package/dist/a2a/client.js +645 -0
  18. package/dist/a2a/handlers.d.ts +4 -0
  19. package/dist/a2a/handlers.d.ts.map +1 -0
  20. package/dist/a2a/handlers.js +656 -0
  21. package/dist/a2a/transfer.d.ts +18 -0
  22. package/dist/a2a/transfer.d.ts.map +1 -0
  23. package/dist/a2a/transfer.js +22 -0
  24. package/dist/a2a/types.d.ts +63 -0
  25. package/dist/a2a/types.d.ts.map +1 -0
  26. package/dist/a2a/types.js +1 -0
  27. package/dist/agents/Agent.d.ts +151 -0
  28. package/dist/agents/Agent.d.ts.map +1 -0
  29. package/dist/agents/Agent.js +1164 -0
  30. package/dist/agents/ModelFactory.d.ts +62 -0
  31. package/dist/agents/ModelFactory.d.ts.map +1 -0
  32. package/dist/agents/ModelFactory.js +208 -0
  33. package/dist/agents/SystemPromptBuilder.d.ts +14 -0
  34. package/dist/agents/SystemPromptBuilder.d.ts.map +1 -0
  35. package/dist/agents/SystemPromptBuilder.js +62 -0
  36. package/dist/agents/ToolSessionManager.d.ts +53 -0
  37. package/dist/agents/ToolSessionManager.d.ts.map +1 -0
  38. package/dist/agents/ToolSessionManager.js +106 -0
  39. package/dist/agents/artifactTools.d.ts +30 -0
  40. package/dist/agents/artifactTools.d.ts.map +1 -0
  41. package/dist/agents/artifactTools.js +463 -0
  42. package/dist/agents/generateTaskHandler.d.ts +41 -0
  43. package/dist/agents/generateTaskHandler.d.ts.map +1 -0
  44. package/dist/agents/generateTaskHandler.js +350 -0
  45. package/dist/agents/relationTools.d.ts +35 -0
  46. package/dist/agents/relationTools.d.ts.map +1 -0
  47. package/dist/agents/relationTools.js +246 -0
  48. package/dist/agents/types.d.ts +23 -0
  49. package/dist/agents/types.d.ts.map +1 -0
  50. package/dist/agents/types.js +1 -0
  51. package/dist/agents/versions/V1Config.d.ts +21 -0
  52. package/dist/agents/versions/V1Config.d.ts.map +1 -0
  53. package/dist/agents/versions/V1Config.js +285 -0
  54. package/dist/app.d.ts +5 -0
  55. package/dist/app.d.ts.map +1 -0
  56. package/dist/app.js +219 -0
  57. package/dist/data/agentGraph.d.ts +4 -0
  58. package/dist/data/agentGraph.d.ts.map +1 -0
  59. package/dist/data/agentGraph.js +73 -0
  60. package/dist/data/agents.d.ts +4 -0
  61. package/dist/data/agents.d.ts.map +1 -0
  62. package/dist/data/agents.js +78 -0
  63. package/dist/data/conversations.d.ts +59 -0
  64. package/dist/data/conversations.d.ts.map +1 -0
  65. package/dist/data/conversations.js +216 -0
  66. package/dist/data/db/clean.d.ts +6 -0
  67. package/dist/data/db/clean.d.ts.map +1 -0
  68. package/dist/data/db/clean.js +77 -0
  69. package/dist/data/db/dbClient.d.ts +3 -0
  70. package/dist/data/db/dbClient.d.ts.map +1 -0
  71. package/dist/data/db/dbClient.js +13 -0
  72. package/dist/env.d.ts +45 -0
  73. package/dist/env.d.ts.map +1 -0
  74. package/dist/env.js +64 -0
  75. package/dist/handlers/executionHandler.d.ts +36 -0
  76. package/dist/handlers/executionHandler.d.ts.map +1 -0
  77. package/dist/handlers/executionHandler.js +415 -0
  78. package/dist/index.d.ts +11 -0
  79. package/dist/index.d.ts.map +1 -0
  80. package/dist/index.js +28 -0
  81. package/dist/instrumentation.d.ts +13 -0
  82. package/dist/instrumentation.d.ts.map +1 -0
  83. package/dist/instrumentation.js +66 -0
  84. package/dist/logger.d.ts +4 -0
  85. package/dist/logger.d.ts.map +1 -0
  86. package/dist/logger.js +32 -0
  87. package/dist/middleware/api-key-auth.d.ts +22 -0
  88. package/dist/middleware/api-key-auth.d.ts.map +1 -0
  89. package/dist/middleware/api-key-auth.js +139 -0
  90. package/dist/middleware/index.d.ts +2 -0
  91. package/dist/middleware/index.d.ts.map +1 -0
  92. package/dist/middleware/index.js +1 -0
  93. package/dist/openapi.d.ts +2 -0
  94. package/dist/openapi.d.ts.map +1 -0
  95. package/dist/openapi.js +36 -0
  96. package/dist/routes/agents.d.ts +10 -0
  97. package/dist/routes/agents.d.ts.map +1 -0
  98. package/dist/routes/agents.js +158 -0
  99. package/dist/routes/chat.d.ts +10 -0
  100. package/dist/routes/chat.d.ts.map +1 -0
  101. package/dist/routes/chat.js +307 -0
  102. package/dist/routes/chatDataStream.d.ts +10 -0
  103. package/dist/routes/chatDataStream.d.ts.map +1 -0
  104. package/dist/routes/chatDataStream.js +185 -0
  105. package/dist/routes/mcp.d.ts +10 -0
  106. package/dist/routes/mcp.d.ts.map +1 -0
  107. package/dist/routes/mcp.js +500 -0
  108. package/dist/tracer.d.ts +24 -0
  109. package/dist/tracer.d.ts.map +1 -0
  110. package/dist/tracer.js +107 -0
  111. package/dist/types/chat.d.ts +25 -0
  112. package/dist/types/chat.d.ts.map +1 -0
  113. package/dist/types/chat.js +1 -0
  114. package/dist/types/execution-context.d.ts +14 -0
  115. package/dist/types/execution-context.d.ts.map +1 -0
  116. package/dist/types/execution-context.js +14 -0
  117. package/dist/utils/agent-operations.d.ts +93 -0
  118. package/dist/utils/agent-operations.d.ts.map +1 -0
  119. package/dist/utils/agent-operations.js +78 -0
  120. package/dist/utils/artifact-component-schema.d.ts +29 -0
  121. package/dist/utils/artifact-component-schema.d.ts.map +1 -0
  122. package/dist/utils/artifact-component-schema.js +119 -0
  123. package/dist/utils/artifact-parser.d.ts +71 -0
  124. package/dist/utils/artifact-parser.d.ts.map +1 -0
  125. package/dist/utils/artifact-parser.js +253 -0
  126. package/dist/utils/cleanup.d.ts +19 -0
  127. package/dist/utils/cleanup.d.ts.map +1 -0
  128. package/dist/utils/cleanup.js +66 -0
  129. package/dist/utils/data-component-schema.d.ts +6 -0
  130. package/dist/utils/data-component-schema.d.ts.map +1 -0
  131. package/dist/utils/data-component-schema.js +43 -0
  132. package/dist/utils/graph-session.d.ts +230 -0
  133. package/dist/utils/graph-session.d.ts.map +1 -0
  134. package/dist/utils/graph-session.js +1199 -0
  135. package/dist/utils/incremental-stream-parser.d.ts +62 -0
  136. package/dist/utils/incremental-stream-parser.d.ts.map +1 -0
  137. package/dist/utils/incremental-stream-parser.js +330 -0
  138. package/dist/utils/response-formatter.d.ts +26 -0
  139. package/dist/utils/response-formatter.d.ts.map +1 -0
  140. package/dist/utils/response-formatter.js +158 -0
  141. package/dist/utils/stream-helpers.d.ts +186 -0
  142. package/dist/utils/stream-helpers.d.ts.map +1 -0
  143. package/dist/utils/stream-helpers.js +603 -0
  144. package/dist/utils/stream-registry.d.ts +18 -0
  145. package/dist/utils/stream-registry.d.ts.map +1 -0
  146. package/dist/utils/stream-registry.js +33 -0
  147. package/package.json +95 -0
  148. package/templates/v1/artifact.xml +7 -0
  149. package/templates/v1/data-component.xml +9 -0
  150. package/templates/v1/system-prompt.xml +52 -0
  151. package/templates/v1/thinking-preparation.xml +34 -0
  152. package/templates/v1/tool.xml +12 -0
@@ -0,0 +1,14 @@
1
+ /**
2
+ * Create execution context from middleware values
3
+ */
4
+ export function createExecutionContext(params) {
5
+ return {
6
+ apiKey: params.apiKey,
7
+ tenantId: params.tenantId,
8
+ projectId: params.projectId,
9
+ graphId: params.graphId,
10
+ baseUrl: params.baseUrl || process.env.API_URL || 'http://localhost:3003',
11
+ apiKeyId: params.apiKeyId,
12
+ agentId: params.agentId,
13
+ };
14
+ }
@@ -0,0 +1,93 @@
1
+ /**
2
+ * Agent initialization operation event
3
+ */
4
+ export interface AgentInitializingEvent {
5
+ type: 'agent_initializing';
6
+ ctx: {
7
+ sessionId: string;
8
+ graphId: string;
9
+ };
10
+ }
11
+ /**
12
+ * Agent ready operation event
13
+ */
14
+ export interface AgentReadyEvent {
15
+ type: 'agent_ready';
16
+ ctx: {
17
+ sessionId: string;
18
+ graphId: string;
19
+ };
20
+ }
21
+ /**
22
+ * Completion operation event
23
+ */
24
+ export interface CompletionEvent {
25
+ type: 'completion';
26
+ ctx: {
27
+ agent: string;
28
+ iteration: number;
29
+ };
30
+ }
31
+ /**
32
+ * Error operation event
33
+ */
34
+ export interface ErrorEvent {
35
+ type: 'error';
36
+ ctx: {
37
+ error: string;
38
+ agent?: string;
39
+ };
40
+ }
41
+ /**
42
+ * Agent thinking operation event
43
+ */
44
+ export interface AgentThinkingEvent {
45
+ type: 'agent_thinking';
46
+ ctx: {
47
+ agent: string;
48
+ };
49
+ }
50
+ /**
51
+ * Status update operation event with flexible structured/unstructured data
52
+ */
53
+ export interface StatusUpdateEvent {
54
+ type: 'status_update';
55
+ label?: string;
56
+ ctx: {
57
+ summary?: string;
58
+ [key: string]: any;
59
+ };
60
+ }
61
+ /**
62
+ * Discriminated union of all operation events
63
+ */
64
+ export type OperationEvent = AgentInitializingEvent | AgentReadyEvent | AgentThinkingEvent | CompletionEvent | ErrorEvent | StatusUpdateEvent;
65
+ /**
66
+ * Creates an agent initializing operation
67
+ */
68
+ export declare function agentInitializingOp(sessionId: string, graphId: string): AgentInitializingEvent;
69
+ /**
70
+ * Creates an agent ready operation
71
+ */
72
+ export declare function agentReadyOp(sessionId: string, graphId: string): AgentReadyEvent;
73
+ /**
74
+ * Creates an agent thinking operation
75
+ */
76
+ export declare function agentThinkingOp(agent: string): AgentThinkingEvent;
77
+ /**
78
+ * Creates a completion operation
79
+ */
80
+ export declare function completionOp(agentId: string, iterations: number): CompletionEvent;
81
+ /**
82
+ * Creates an error operation
83
+ */
84
+ export declare function errorOp(error: string, agentId?: string): ErrorEvent;
85
+ /**
86
+ * Generate a unique tool execution ID for lifecycle tracking
87
+ */
88
+ export declare function generateToolId(): string;
89
+ /**
90
+ * Creates a status update operation with flexible data
91
+ */
92
+ export declare function statusUpdateOp(ctx: Record<string, any>): StatusUpdateEvent;
93
+ //# sourceMappingURL=agent-operations.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent-operations.d.ts","sourceRoot":"","sources":["../../src/utils/agent-operations.ts"],"names":[],"mappings":"AAMA;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACrC,IAAI,EAAE,oBAAoB,CAAC;IAC3B,GAAG,EAAE;QACH,SAAS,EAAE,MAAM,CAAC;QAClB,OAAO,EAAE,MAAM,CAAC;KACjB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,aAAa,CAAC;IACpB,GAAG,EAAE;QACH,SAAS,EAAE,MAAM,CAAC;QAClB,OAAO,EAAE,MAAM,CAAC;KACjB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,YAAY,CAAC;IACnB,GAAG,EAAE;QACH,KAAK,EAAE,MAAM,CAAC;QACd,SAAS,EAAE,MAAM,CAAC;KACnB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,OAAO,CAAC;IACd,GAAG,EAAE;QACH,KAAK,EAAE,MAAM,CAAC;QACd,KAAK,CAAC,EAAE,MAAM,CAAC;KAChB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,gBAAgB,CAAC;IACvB,GAAG,EAAE;QACH,KAAK,EAAE,MAAM,CAAC;KACf,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,eAAe,CAAC;IACtB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,GAAG,EAAE;QACH,OAAO,CAAC,EAAE,MAAM,CAAC;QACjB,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAC;KACpB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,MAAM,cAAc,GACtB,sBAAsB,GACtB,eAAe,GACf,kBAAkB,GAClB,eAAe,GACf,UAAU,GACV,iBAAiB,CAAC;AAMtB;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,sBAAsB,CAQ9F;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,eAAe,CAQhF;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,KAAK,EAAE,MAAM,GAAG,kBAAkB,CAOjE;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,eAAe,CAQjF;AAED;;GAEG;AACH,wBAAgB,OAAO,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,MAAM,GAAG,UAAU,CAQnE;AAED;;GAEG;AACH,wBAAgB,cAAc,IAAI,MAAM,CAEvC;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,iBAAiB,CAK1E"}
@@ -0,0 +1,78 @@
1
+ import { nanoid } from 'nanoid';
2
+ // =============================================================================
3
+ // OPERATION FUNCTIONS
4
+ // =============================================================================
5
+ /**
6
+ * Creates an agent initializing operation
7
+ */
8
+ export function agentInitializingOp(sessionId, graphId) {
9
+ return {
10
+ type: 'agent_initializing',
11
+ ctx: {
12
+ sessionId,
13
+ graphId,
14
+ },
15
+ };
16
+ }
17
+ /**
18
+ * Creates an agent ready operation
19
+ */
20
+ export function agentReadyOp(sessionId, graphId) {
21
+ return {
22
+ type: 'agent_ready',
23
+ ctx: {
24
+ sessionId,
25
+ graphId,
26
+ },
27
+ };
28
+ }
29
+ /**
30
+ * Creates an agent thinking operation
31
+ */
32
+ export function agentThinkingOp(agent) {
33
+ return {
34
+ type: 'agent_thinking',
35
+ ctx: {
36
+ agent,
37
+ },
38
+ };
39
+ }
40
+ /**
41
+ * Creates a completion operation
42
+ */
43
+ export function completionOp(agentId, iterations) {
44
+ return {
45
+ type: 'completion',
46
+ ctx: {
47
+ agent: agentId,
48
+ iteration: iterations,
49
+ },
50
+ };
51
+ }
52
+ /**
53
+ * Creates an error operation
54
+ */
55
+ export function errorOp(error, agentId) {
56
+ return {
57
+ type: 'error',
58
+ ctx: {
59
+ error,
60
+ agent: agentId,
61
+ },
62
+ };
63
+ }
64
+ /**
65
+ * Generate a unique tool execution ID for lifecycle tracking
66
+ */
67
+ export function generateToolId() {
68
+ return `tool_${nanoid(8)}`;
69
+ }
70
+ /**
71
+ * Creates a status update operation with flexible data
72
+ */
73
+ export function statusUpdateOp(ctx) {
74
+ return {
75
+ type: 'status_update',
76
+ ctx,
77
+ };
78
+ }
@@ -0,0 +1,29 @@
1
+ import type { ArtifactComponentApiSelect, DataComponentInsert } from '@inkeep/agents-core';
2
+ import { z } from 'zod';
3
+ /**
4
+ * Converts artifact component configurations to Zod schema for structured generation
5
+ */
6
+ export declare function createArtifactComponentsSchema(artifactComponents?: ArtifactComponentApiSelect[]): z.ZodObject<{}, z.core.$strip> | z.ZodUnion<any>;
7
+ /**
8
+ * Create schema for artifact component summary props only (for quick display)
9
+ */
10
+ export declare function createArtifactComponentsSummarySchema(artifactComponents?: ArtifactComponentApiSelect[]): z.ZodUnion<any> | z.ZodObject<{}, z.core.$strip>;
11
+ /**
12
+ * Create schema for artifact component full props only (for detailed display)
13
+ */
14
+ export declare function createArtifactComponentsFullSchema(artifactComponents?: ArtifactComponentApiSelect[]): z.ZodUnion<any> | z.ZodObject<{}, z.core.$strip>;
15
+ /**
16
+ * Standard artifact reference component schema for tool responses
17
+ */
18
+ export declare class ArtifactReferenceSchema {
19
+ private static readonly ARTIFACT_PROPS_SCHEMA;
20
+ /**
21
+ * Get the standard Zod schema for artifact reference components
22
+ */
23
+ static getSchema(): z.ZodType<any>;
24
+ /**
25
+ * Get complete DataComponent by adding missing fields to base definition
26
+ */
27
+ static getDataComponent(tenantId: string, projectId?: string): DataComponentInsert;
28
+ }
29
+ //# sourceMappingURL=artifact-component-schema.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"artifact-component-schema.d.ts","sourceRoot":"","sources":["../../src/utils/artifact-component-schema.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,0BAA0B,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC3F,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAMxB;;GAEG;AACH,wBAAgB,8BAA8B,CAAC,kBAAkB,CAAC,EAAE,0BAA0B,EAAE,oDA2B/F;AAED;;GAEG;AACH,wBAAgB,qCAAqC,CACnD,kBAAkB,CAAC,EAAE,0BAA0B,EAAE,oDAsBlD;AAED;;GAEG;AACH,wBAAgB,kCAAkC,CAChD,kBAAkB,CAAC,EAAE,0BAA0B,EAAE,oDAsBlD;AAED;;GAEG;AACH,qBAAa,uBAAuB;IAElC,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,qBAAqB,CAe3C;IAEF;;OAEG;IACH,MAAM,CAAC,SAAS,IAAI,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC;IAQlC;;OAEG;IACH,MAAM,CAAC,gBAAgB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,GAAE,MAAW,GAAG,mBAAmB;CAWvF"}
@@ -0,0 +1,119 @@
1
+ import { z } from 'zod';
2
+ import { getLogger } from '../logger';
3
+ import { jsonSchemaToZod } from './data-component-schema';
4
+ const _logger = getLogger('ArtifactComponentSchema');
5
+ /**
6
+ * Converts artifact component configurations to Zod schema for structured generation
7
+ */
8
+ export function createArtifactComponentsSchema(artifactComponents) {
9
+ // Convert artifact component configs to a union schema
10
+ const componentSchemas = artifactComponents?.map((component) => {
11
+ // Convert the JSON Schema props to Zod - handle both summaryProps and fullProps
12
+ const summaryPropsSchema = jsonSchemaToZod(component.summaryProps);
13
+ const fullPropsSchema = jsonSchemaToZod(component.fullProps);
14
+ // Return schema with both summary and full props
15
+ return z
16
+ .object({
17
+ id: z.string().describe(component.id),
18
+ name: z.literal(component.name).describe(component.name),
19
+ summaryProps: summaryPropsSchema,
20
+ fullProps: fullPropsSchema,
21
+ })
22
+ .describe(`${component.name}: ${component.description}`);
23
+ }) || [];
24
+ // Return union of all component schemas - z.union requires at least 2 schemas
25
+ if (componentSchemas.length === 0) {
26
+ return z.object({}); // Empty object for no components
27
+ }
28
+ if (componentSchemas.length === 1) {
29
+ return componentSchemas[0]; // Single schema doesn't need union
30
+ }
31
+ return z.union(componentSchemas); // Safe union with 2+ schemas
32
+ }
33
+ /**
34
+ * Create schema for artifact component summary props only (for quick display)
35
+ */
36
+ export function createArtifactComponentsSummarySchema(artifactComponents) {
37
+ const componentSchemas = artifactComponents?.map((component) => {
38
+ const summaryPropsSchema = jsonSchemaToZod(component.summaryProps);
39
+ return z
40
+ .object({
41
+ id: z.string().describe(component.id),
42
+ name: z.literal(component.name).describe(component.name),
43
+ summaryProps: summaryPropsSchema,
44
+ })
45
+ .describe(`${component.name} Summary: ${component.description}`);
46
+ }) || [];
47
+ if (componentSchemas.length === 0) {
48
+ return z.object({});
49
+ }
50
+ if (componentSchemas.length === 1) {
51
+ return componentSchemas[0];
52
+ }
53
+ return z.union(componentSchemas);
54
+ }
55
+ /**
56
+ * Create schema for artifact component full props only (for detailed display)
57
+ */
58
+ export function createArtifactComponentsFullSchema(artifactComponents) {
59
+ const componentSchemas = artifactComponents?.map((component) => {
60
+ const fullPropsSchema = jsonSchemaToZod(component.fullProps);
61
+ return z
62
+ .object({
63
+ id: z.string().describe(component.id),
64
+ name: z.literal(component.name).describe(component.name),
65
+ fullProps: fullPropsSchema,
66
+ })
67
+ .describe(`${component.name} Full: ${component.description}`);
68
+ }) || [];
69
+ if (componentSchemas.length === 0) {
70
+ return z.object({});
71
+ }
72
+ if (componentSchemas.length === 1) {
73
+ return componentSchemas[0];
74
+ }
75
+ return z.union(componentSchemas);
76
+ }
77
+ /**
78
+ * Standard artifact reference component schema for tool responses
79
+ */
80
+ export class ArtifactReferenceSchema {
81
+ // Standard artifact props schema - single source of truth
82
+ static ARTIFACT_PROPS_SCHEMA = {
83
+ type: 'object',
84
+ properties: {
85
+ artifact_id: {
86
+ type: 'string',
87
+ description: 'The EXACT artifact_id from save_tool_result tool output. NEVER invent or make up IDs.',
88
+ },
89
+ task_id: {
90
+ type: 'string',
91
+ description: 'The EXACT task_id from save_tool_result tool output. NEVER invent or make up IDs.',
92
+ },
93
+ },
94
+ required: ['artifact_id', 'task_id'],
95
+ };
96
+ /**
97
+ * Get the standard Zod schema for artifact reference components
98
+ */
99
+ static getSchema() {
100
+ return z.object({
101
+ id: z.string(),
102
+ name: z.literal('Artifact'),
103
+ props: jsonSchemaToZod(ArtifactReferenceSchema.ARTIFACT_PROPS_SCHEMA),
104
+ });
105
+ }
106
+ /**
107
+ * Get complete DataComponent by adding missing fields to base definition
108
+ */
109
+ static getDataComponent(tenantId, projectId = '') {
110
+ return {
111
+ id: 'The EXACT artifact_id from save_tool_result tool output. NEVER invent or make up IDs.',
112
+ tenantId: tenantId,
113
+ projectId: projectId,
114
+ name: 'Artifact',
115
+ description: 'Reference to saved content from tool results that grounds information in verifiable sources.',
116
+ props: ArtifactReferenceSchema.ARTIFACT_PROPS_SCHEMA,
117
+ };
118
+ }
119
+ }
@@ -0,0 +1,71 @@
1
+ export interface StreamPart {
2
+ kind: 'text' | 'data';
3
+ text?: string;
4
+ data?: any;
5
+ }
6
+ export interface ArtifactData {
7
+ artifactId: string;
8
+ taskId: string;
9
+ name: string;
10
+ description: string;
11
+ artifactType?: string;
12
+ artifactSummary: any;
13
+ }
14
+ /**
15
+ * Unified artifact parser that handles all artifact-related parsing and formatting
16
+ * Used by both ResponseFormatter and IncrementalStreamParser to eliminate redundancy
17
+ */
18
+ export declare class ArtifactParser {
19
+ private tenantId;
20
+ private static readonly ARTIFACT_REGEX;
21
+ private static readonly ARTIFACT_CHECK_REGEX;
22
+ private static readonly INCOMPLETE_ARTIFACT_REGEX;
23
+ constructor(tenantId: string);
24
+ /**
25
+ * Check if text contains complete artifact markers
26
+ */
27
+ hasArtifactMarkers(text: string): boolean;
28
+ /**
29
+ * Check if text has incomplete artifact marker (for streaming)
30
+ * More robust detection that handles streaming fragments
31
+ */
32
+ hasIncompleteArtifact(text: string): boolean;
33
+ /**
34
+ * Find safe text boundary before incomplete artifacts (for streaming)
35
+ * Enhanced to handle streaming chunks that split in the middle of artifacts
36
+ */
37
+ findSafeTextBoundary(text: string): number;
38
+ /**
39
+ * Get all artifacts for a context (with caching opportunity)
40
+ */
41
+ getContextArtifacts(contextId: string): Promise<Map<string, any>>;
42
+ /**
43
+ * Convert raw artifact to standardized data format
44
+ */
45
+ private formatArtifactData;
46
+ /**
47
+ * Parse text with artifact markers into parts array
48
+ * Can work with or without pre-fetched artifact map
49
+ */
50
+ parseText(text: string, artifactMap?: Map<string, any>): Promise<StreamPart[]>;
51
+ /**
52
+ * Process object/dataComponents for artifact components
53
+ */
54
+ parseObject(obj: any, artifactMap?: Map<string, any>): Promise<StreamPart[]>;
55
+ /**
56
+ * Check if object is an artifact component
57
+ */
58
+ private isArtifactComponent;
59
+ /**
60
+ * Get artifact data from map or fetch directly
61
+ */
62
+ private getArtifactData;
63
+ /**
64
+ * Parse partial JSON buffer (for streaming)
65
+ */
66
+ parsePartialJSON(buffer: string): {
67
+ complete: any[];
68
+ remaining: string;
69
+ };
70
+ }
71
+ //# sourceMappingURL=artifact-parser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"artifact-parser.d.ts","sourceRoot":"","sources":["../../src/utils/artifact-parser.ts"],"names":[],"mappings":"AAOA,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,MAAM,GAAG,MAAM,CAAC;IACtB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,GAAG,CAAC;CACZ;AAED,MAAM,WAAW,YAAY;IAC3B,UAAU,EAAE,MAAM,CAAC;IACnB,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,eAAe,EAAE,GAAG,CAAC;CACtB;AAED;;;GAGG;AACH,qBAAa,cAAc;IAWb,OAAO,CAAC,QAAQ;IAT5B,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,cAAc,CACsB;IAC5D,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,oBAAoB,CACmB;IAG/D,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,yBAAyB,CACQ;gBAErC,QAAQ,EAAE,MAAM;IAEpC;;OAEG;IACH,kBAAkB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;IAIzC;;;OAGG;IACH,qBAAqB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO;IAU5C;;;OAGG;IACH,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM;IAqC1C;;OAEG;IACG,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAqCvE;;OAEG;IACH,OAAO,CAAC,kBAAkB;IAW1B;;;OAGG;IACG,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,UAAU,EAAE,CAAC;IA2CpF;;OAEG;IACG,WAAW,CAAC,GAAG,EAAE,GAAG,EAAE,WAAW,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,OAAO,CAAC,UAAU,EAAE,CAAC;IAoClF;;OAEG;IACH,OAAO,CAAC,mBAAmB;IAI3B;;OAEG;YACW,eAAe;IAwC7B;;OAEG;IACH,gBAAgB,CAAC,MAAM,EAAE,MAAM,GAAG;QAAE,QAAQ,EAAE,GAAG,EAAE,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE;CA2BzE"}
@@ -0,0 +1,253 @@
1
+ import { getLedgerArtifacts, getTask, listTaskIdsByContextId } from '@inkeep/agents-core';
2
+ import dbClient from '../data/db/dbClient';
3
+ import { getLogger } from '../logger';
4
+ const logger = getLogger('ArtifactParser');
5
+ /**
6
+ * Unified artifact parser that handles all artifact-related parsing and formatting
7
+ * Used by both ResponseFormatter and IncrementalStreamParser to eliminate redundancy
8
+ */
9
+ export class ArtifactParser {
10
+ tenantId;
11
+ // Shared regex patterns
12
+ static ARTIFACT_REGEX = /<artifact:ref\s+id="([^"]*?)"\s+task="([^"]*?)"\s*\/>/gs;
13
+ static ARTIFACT_CHECK_REGEX = /<artifact:ref\s+(?=.*id="[^"]+")(?=.*task="[^"]+")[^>]*\/>/;
14
+ // Regex for catching any partial artifact pattern (< + any prefix of "artifact:ref")
15
+ static INCOMPLETE_ARTIFACT_REGEX = /<(a(r(t(i(f(a(c(t(:(r(e(f?)?)?)?)?)?)?)?)?)?)?)?)?$/g;
16
+ constructor(tenantId) {
17
+ this.tenantId = tenantId;
18
+ }
19
+ /**
20
+ * Check if text contains complete artifact markers
21
+ */
22
+ hasArtifactMarkers(text) {
23
+ return ArtifactParser.ARTIFACT_CHECK_REGEX.test(text);
24
+ }
25
+ /**
26
+ * Check if text has incomplete artifact marker (for streaming)
27
+ * More robust detection that handles streaming fragments
28
+ */
29
+ hasIncompleteArtifact(text) {
30
+ // Use safe, non-backtracking patterns to prevent ReDoS attacks
31
+ // Check if text ends with any partial artifact pattern
32
+ return (/^.*<(?:artifact(?::ref)?|a(?:r(?:t(?:i(?:f(?:a(?:c(?:t(?::(?:r(?:e(?:f)?)?)?)?)?)?)?)?)?)?)?)?$/.test(text) ||
33
+ /^.*<artifact:ref(?:[^>]*)$/.test(text) || // Incomplete artifact:ref at end
34
+ this.findSafeTextBoundary(text) < text.length);
35
+ }
36
+ /**
37
+ * Find safe text boundary before incomplete artifacts (for streaming)
38
+ * Enhanced to handle streaming chunks that split in the middle of artifacts
39
+ */
40
+ findSafeTextBoundary(text) {
41
+ // First check for incomplete artifact patterns at the end
42
+ // Use safe patterns that don't cause exponential backtracking
43
+ const endPatterns = [
44
+ /^.*<artifact:ref(?:[^/>]+(?:[^>]*[^/])?)?$/, // artifact:ref that doesn't end with />
45
+ /^.*<(?:artifact(?::ref)?|a(?:r(?:t(?:i(?:f(?:a(?:c(?:t(?::(?:r(?:e(?:f)?)?)?)?)?)?)?)?)?)?)?)?$/, // Safe partial artifact pattern
46
+ ];
47
+ for (const pattern of endPatterns) {
48
+ const match = text.match(pattern);
49
+ if (match && match.index !== undefined) {
50
+ return match.index;
51
+ }
52
+ }
53
+ // Look for incomplete artifact patterns anywhere in text
54
+ const matches = [...text.matchAll(ArtifactParser.INCOMPLETE_ARTIFACT_REGEX)];
55
+ if (matches.length === 0) {
56
+ return text.length;
57
+ }
58
+ // Check each match from the end to find an incomplete artifact
59
+ for (let i = matches.length - 1; i >= 0; i--) {
60
+ const match = matches[i];
61
+ const startIdx = match.index;
62
+ const textAfterMatch = text.slice(startIdx);
63
+ // If the text after this match doesn't contain a closing '/>', it's incomplete
64
+ if (!textAfterMatch.includes('/>')) {
65
+ return startIdx;
66
+ }
67
+ }
68
+ return text.length;
69
+ }
70
+ /**
71
+ * Get all artifacts for a context (with caching opportunity)
72
+ */
73
+ async getContextArtifacts(contextId) {
74
+ const artifacts = new Map();
75
+ try {
76
+ const taskIds = await listTaskIdsByContextId(dbClient)({
77
+ contextId: contextId,
78
+ });
79
+ for (const taskId of taskIds) {
80
+ // Get task to retrieve projectId
81
+ const task = await getTask(dbClient)({
82
+ id: taskId,
83
+ });
84
+ if (!task) {
85
+ logger.warn({ taskId }, 'Task not found when fetching artifacts');
86
+ continue;
87
+ }
88
+ const taskArtifacts = await getLedgerArtifacts(dbClient)({
89
+ scopes: { tenantId: this.tenantId, projectId: task.projectId },
90
+ taskId,
91
+ });
92
+ for (const artifact of taskArtifacts) {
93
+ const key = `${artifact.artifactId}:${artifact.taskId}`;
94
+ artifacts.set(key, artifact);
95
+ }
96
+ }
97
+ logger.debug({ contextId, count: artifacts.size }, 'Loaded context artifacts');
98
+ }
99
+ catch (error) {
100
+ logger.error({ error, contextId }, 'Error loading context artifacts');
101
+ }
102
+ return artifacts;
103
+ }
104
+ /**
105
+ * Convert raw artifact to standardized data format
106
+ */
107
+ formatArtifactData(artifact, artifactId, taskId) {
108
+ return {
109
+ artifactId,
110
+ taskId,
111
+ name: artifact.name || 'Processing...',
112
+ description: artifact.description || 'Name and description being generated...',
113
+ artifactType: artifact.metadata?.artifactType,
114
+ artifactSummary: artifact.parts?.[0]?.data?.summary || {},
115
+ };
116
+ }
117
+ /**
118
+ * Parse text with artifact markers into parts array
119
+ * Can work with or without pre-fetched artifact map
120
+ */
121
+ async parseText(text, artifactMap) {
122
+ const parts = [];
123
+ const matches = [...text.matchAll(ArtifactParser.ARTIFACT_REGEX)];
124
+ if (matches.length === 0) {
125
+ return [{ kind: 'text', text }];
126
+ }
127
+ let lastIndex = 0;
128
+ for (const match of matches) {
129
+ const [fullMatch, artifactId, taskId] = match;
130
+ const matchStart = match.index;
131
+ // Add text before artifact
132
+ if (matchStart > lastIndex) {
133
+ const textBefore = text.slice(lastIndex, matchStart);
134
+ if (textBefore.trim()) {
135
+ parts.push({ kind: 'text', text: textBefore });
136
+ }
137
+ }
138
+ // Get artifact data
139
+ const artifactData = await this.getArtifactData(artifactId, taskId, artifactMap);
140
+ if (artifactData) {
141
+ parts.push({ kind: 'data', data: artifactData });
142
+ }
143
+ // If no artifact found, marker is simply removed
144
+ lastIndex = matchStart + fullMatch.length;
145
+ }
146
+ // Add remaining text
147
+ if (lastIndex < text.length) {
148
+ const remainingText = text.slice(lastIndex);
149
+ if (remainingText.trim()) {
150
+ parts.push({ kind: 'text', text: remainingText });
151
+ }
152
+ }
153
+ return parts;
154
+ }
155
+ /**
156
+ * Process object/dataComponents for artifact components
157
+ */
158
+ async parseObject(obj, artifactMap) {
159
+ // Handle dataComponents array
160
+ if (obj?.dataComponents && Array.isArray(obj.dataComponents)) {
161
+ const parts = [];
162
+ for (const component of obj.dataComponents) {
163
+ if (this.isArtifactComponent(component)) {
164
+ const artifactData = await this.getArtifactData(component.props.artifact_id, component.props.task_id, artifactMap);
165
+ if (artifactData) {
166
+ parts.push({ kind: 'data', data: artifactData });
167
+ }
168
+ }
169
+ else {
170
+ parts.push({ kind: 'data', data: component });
171
+ }
172
+ }
173
+ return parts;
174
+ }
175
+ // Handle single object
176
+ if (this.isArtifactComponent(obj)) {
177
+ const artifactData = await this.getArtifactData(obj.props.artifact_id, obj.props.task_id, artifactMap);
178
+ return artifactData ? [{ kind: 'data', data: artifactData }] : [];
179
+ }
180
+ return [{ kind: 'data', data: obj }];
181
+ }
182
+ /**
183
+ * Check if object is an artifact component
184
+ */
185
+ isArtifactComponent(obj) {
186
+ return obj?.props?.artifact_id && obj?.props?.task_id;
187
+ }
188
+ /**
189
+ * Get artifact data from map or fetch directly
190
+ */
191
+ async getArtifactData(artifactId, taskId, artifactMap) {
192
+ const key = `${artifactId}:${taskId}`;
193
+ // Try map first
194
+ if (artifactMap?.has(key)) {
195
+ const artifact = artifactMap.get(key);
196
+ return this.formatArtifactData(artifact, artifactId, taskId);
197
+ }
198
+ // Fetch directly if no map
199
+ try {
200
+ // Get task to retrieve projectId
201
+ const task = await getTask(dbClient)({
202
+ id: taskId,
203
+ });
204
+ if (!task) {
205
+ logger.warn({ taskId }, 'Task not found when fetching artifact');
206
+ return null;
207
+ }
208
+ const artifacts = await getLedgerArtifacts(dbClient)({
209
+ scopes: { tenantId: this.tenantId, projectId: task.projectId },
210
+ artifactId,
211
+ taskId,
212
+ });
213
+ if (artifacts.length > 0) {
214
+ return this.formatArtifactData(artifacts[0], artifactId, taskId);
215
+ }
216
+ }
217
+ catch (error) {
218
+ logger.warn({ artifactId, taskId, error }, 'Failed to fetch artifact');
219
+ }
220
+ return null;
221
+ }
222
+ /**
223
+ * Parse partial JSON buffer (for streaming)
224
+ */
225
+ parsePartialJSON(buffer) {
226
+ const complete = [];
227
+ let remaining = buffer;
228
+ let braceCount = 0;
229
+ let start = -1;
230
+ for (let i = 0; i < buffer.length; i++) {
231
+ if (buffer[i] === '{') {
232
+ if (braceCount === 0)
233
+ start = i;
234
+ braceCount++;
235
+ }
236
+ else if (buffer[i] === '}') {
237
+ braceCount--;
238
+ if (braceCount === 0 && start !== -1) {
239
+ const jsonStr = buffer.slice(start, i + 1);
240
+ try {
241
+ complete.push(JSON.parse(jsonStr));
242
+ remaining = buffer.slice(i + 1);
243
+ start = -1;
244
+ }
245
+ catch {
246
+ // Invalid JSON, continue
247
+ }
248
+ }
249
+ }
250
+ }
251
+ return { complete, remaining };
252
+ }
253
+ }