@agentfield/sdk 0.1.64-rc.5 → 0.1.64-rc.7

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.js CHANGED
@@ -1,5 +1,6 @@
1
- import fs from 'fs';
2
- import path from 'path';
1
+ import fs, { promises } from 'fs';
2
+ import * as path2 from 'path';
3
+ import path2__default, { resolve } from 'path';
3
4
  import { createRequire } from 'module';
4
5
  import { spawn } from 'child_process';
5
6
  import express from 'express';
@@ -22,6 +23,7 @@ import https from 'https';
22
23
  import WebSocket from 'ws';
23
24
  import { Buffer as Buffer$1 } from 'buffer';
24
25
  import { zodToJsonSchema } from 'zod-to-json-schema';
26
+ import { readFile } from 'fs/promises';
25
27
 
26
28
  var __defProp = Object.defineProperty;
27
29
  var __getOwnPropNames = Object.getOwnPropertyNames;
@@ -54,12 +56,12 @@ function hasJsonSchema(value) {
54
56
  function hasParse(value) {
55
57
  return isRecord(value) && typeof value.parse === "function";
56
58
  }
57
- function estimateTokens(text) {
58
- return Math.floor(text.length / 4);
59
+ function estimateTokens(text2) {
60
+ return Math.floor(text2.length / 4);
59
61
  }
60
62
  function writeSchemaFile(schemaJson, cwd) {
61
63
  const filePath = getSchemaPath(cwd);
62
- fs.mkdirSync(path.dirname(filePath), { recursive: true });
64
+ fs.mkdirSync(path2__default.dirname(filePath), { recursive: true });
63
65
  const fd = fs.openSync(filePath, "w", 384);
64
66
  try {
65
67
  fs.writeFileSync(fd, schemaJson, "utf8");
@@ -75,10 +77,10 @@ function validateAgainstSchema(data, schema) {
75
77
  return data;
76
78
  }
77
79
  function getOutputPath(cwd) {
78
- return path.join(cwd, OUTPUT_FILENAME);
80
+ return path2__default.join(cwd, OUTPUT_FILENAME);
79
81
  }
80
82
  function getSchemaPath(cwd) {
81
- return path.join(cwd, SCHEMA_FILENAME);
83
+ return path2__default.join(cwd, SCHEMA_FILENAME);
82
84
  }
83
85
  function schemaToJsonSchema(schema) {
84
86
  if (isRecord(schema)) {
@@ -122,24 +124,24 @@ ${schemaJson}
122
124
  Do not include any text outside the JSON in that file. Do not wrap in markdown fences.`;
123
125
  }
124
126
  function cosmeticRepair(raw) {
125
- let text = raw.trim();
126
- const fenceMatch = text.match(/^```(?:json)?\s*\n([\s\S]*?)```\s*$/);
127
+ let text2 = raw.trim();
128
+ const fenceMatch = text2.match(/^```(?:json)?\s*\n([\s\S]*?)```\s*$/);
127
129
  if (fenceMatch) {
128
- text = fenceMatch[1].trim();
130
+ text2 = fenceMatch[1].trim();
129
131
  }
130
- if (text.length > 0 && text[0] !== "{" && text[0] !== "[") {
131
- const firstJsonCharIndex = [...text].findIndex((char) => char === "{" || char === "[");
132
+ if (text2.length > 0 && text2[0] !== "{" && text2[0] !== "[") {
133
+ const firstJsonCharIndex = [...text2].findIndex((char) => char === "{" || char === "[");
132
134
  if (firstJsonCharIndex >= 0) {
133
- text = text.slice(firstJsonCharIndex);
135
+ text2 = text2.slice(firstJsonCharIndex);
134
136
  }
135
137
  }
136
- text = text.replace(/,\s*([}\]])/g, "$1");
137
- const openBraces = (text.match(/{/g)?.length ?? 0) - (text.match(/}/g)?.length ?? 0);
138
- const openBrackets = (text.match(/\[/g)?.length ?? 0) - (text.match(/\]/g)?.length ?? 0);
138
+ text2 = text2.replace(/,\s*([}\]])/g, "$1");
139
+ const openBraces = (text2.match(/{/g)?.length ?? 0) - (text2.match(/}/g)?.length ?? 0);
140
+ const openBrackets = (text2.match(/\[/g)?.length ?? 0) - (text2.match(/\]/g)?.length ?? 0);
139
141
  if (openBraces > 0 || openBrackets > 0) {
140
- text += "]".repeat(openBrackets) + "}".repeat(openBraces);
142
+ text2 += "]".repeat(openBrackets) + "}".repeat(openBraces);
141
143
  }
142
- return text;
144
+ return text2;
143
145
  }
144
146
  function readAndParse(filePath) {
145
147
  try {
@@ -184,7 +186,7 @@ function parseAndValidate(filePath, schema) {
184
186
  function cleanupTempFiles(cwd) {
185
187
  for (const filename of [OUTPUT_FILENAME, SCHEMA_FILENAME]) {
186
188
  try {
187
- fs.unlinkSync(path.join(cwd, filename));
189
+ fs.unlinkSync(path2__default.join(cwd, filename));
188
190
  } catch {
189
191
  }
190
192
  }
@@ -336,7 +338,7 @@ var init_claude = __esm({
336
338
  }
337
339
  });
338
340
  function runCli(cmd, options) {
339
- return new Promise((resolve, reject) => {
341
+ return new Promise((resolve2, reject) => {
340
342
  const [bin, ...args] = cmd;
341
343
  const proc = spawn(bin, args, {
342
344
  env: { ...process.env, ...options?.env },
@@ -359,7 +361,7 @@ function runCli(cmd, options) {
359
361
  if (timer) {
360
362
  clearTimeout(timer);
361
363
  }
362
- resolve({ stdout, stderr, exitCode: code ?? 0 });
364
+ resolve2({ stdout, stderr, exitCode: code ?? 0 });
363
365
  });
364
366
  proc.on("error", (err) => {
365
367
  if (timer) {
@@ -369,9 +371,9 @@ function runCli(cmd, options) {
369
371
  });
370
372
  });
371
373
  }
372
- function parseJsonl(text) {
374
+ function parseJsonl(text2) {
373
375
  const events = [];
374
- for (const line of text.split("\n")) {
376
+ for (const line of text2.split("\n")) {
375
377
  const trimmed = line.trim();
376
378
  if (!trimmed) {
377
379
  continue;
@@ -570,17 +572,30 @@ var init_opencode = __esm({
570
572
  this.bin = binPath;
571
573
  }
572
574
  async execute(prompt, options) {
573
- const cmd = [this.bin, "run"];
575
+ const cmd = [this.bin];
576
+ if (options.cwd && typeof options.cwd === "string") {
577
+ cmd.push("-c", options.cwd);
578
+ } else if (options.project_dir && typeof options.project_dir === "string") {
579
+ cmd.push("-c", options.project_dir);
580
+ }
581
+ const env = { ...options.env };
574
582
  if (options.model) {
575
- cmd.push("--model", String(options.model));
583
+ env["MODEL"] = String(options.model);
576
584
  }
577
- cmd.push(prompt);
585
+ let effectivePrompt = prompt;
586
+ if (options.system_prompt && typeof options.system_prompt === "string" && options.system_prompt.trim()) {
587
+ effectivePrompt = `SYSTEM INSTRUCTIONS:
588
+ ${options.system_prompt.trim()}
589
+
590
+ ---
591
+
592
+ USER REQUEST:
593
+ ${prompt}`;
594
+ }
595
+ cmd.push("-p", effectivePrompt);
578
596
  const startApi = Date.now();
579
597
  try {
580
- const { stdout, stderr, exitCode } = await runCli(cmd, {
581
- env: options.env,
582
- cwd: options.cwd
583
- });
598
+ const { stdout, stderr, exitCode } = await runCli(cmd, { env });
584
599
  const resultText = stdout.trim() || void 0;
585
600
  const isError = exitCode !== 0 && !resultText;
586
601
  return createRawResult({
@@ -817,8 +832,8 @@ var init_runner = __esm({
817
832
  return base + jitter;
818
833
  }
819
834
  sleep(delaySeconds) {
820
- return new Promise((resolve) => {
821
- setTimeout(resolve, Math.max(0, delaySeconds) * 1e3);
835
+ return new Promise((resolve2) => {
836
+ setTimeout(resolve2, Math.max(0, delaySeconds) * 1e3);
822
837
  });
823
838
  }
824
839
  };
@@ -876,6 +891,9 @@ var ExecutionContext = class {
876
891
  this.res = params.res;
877
892
  this.agent = params.agent;
878
893
  }
894
+ get logger() {
895
+ return this.agent.getExecutionLogger();
896
+ }
879
897
  static run(ctx, fn) {
880
898
  return store.run(ctx, fn);
881
899
  }
@@ -1185,13 +1203,16 @@ var ReasonerContext = class {
1185
1203
  sessionId;
1186
1204
  actorId;
1187
1205
  workflowId;
1206
+ rootWorkflowId;
1188
1207
  parentExecutionId;
1208
+ reasonerId;
1189
1209
  callerDid;
1190
1210
  targetDid;
1191
1211
  agentNodeDid;
1192
1212
  req;
1193
1213
  res;
1194
1214
  agent;
1215
+ logger;
1195
1216
  aiClient;
1196
1217
  memory;
1197
1218
  workflow;
@@ -1203,13 +1224,16 @@ var ReasonerContext = class {
1203
1224
  this.sessionId = params.sessionId;
1204
1225
  this.actorId = params.actorId;
1205
1226
  this.workflowId = params.workflowId;
1227
+ this.rootWorkflowId = params.rootWorkflowId;
1206
1228
  this.parentExecutionId = params.parentExecutionId;
1229
+ this.reasonerId = params.reasonerId;
1207
1230
  this.callerDid = params.callerDid;
1208
1231
  this.targetDid = params.targetDid;
1209
1232
  this.agentNodeDid = params.agentNodeDid;
1210
1233
  this.req = params.req;
1211
1234
  this.res = params.res;
1212
1235
  this.agent = params.agent;
1236
+ this.logger = params.logger;
1213
1237
  this.aiClient = params.aiClient;
1214
1238
  this.memory = params.memory;
1215
1239
  this.workflow = params.workflow;
@@ -1263,7 +1287,9 @@ var ReasonerContext = class {
1263
1287
  sessionId: this.sessionId,
1264
1288
  actorId: this.actorId,
1265
1289
  workflowId: this.workflowId,
1290
+ rootWorkflowId: this.rootWorkflowId,
1266
1291
  parentExecutionId: this.parentExecutionId,
1292
+ reasonerId: this.reasonerId,
1267
1293
  callerDid: this.callerDid,
1268
1294
  targetDid: this.targetDid,
1269
1295
  agentNodeDid: this.agentNodeDid
@@ -1281,13 +1307,16 @@ function getCurrentContext() {
1281
1307
  sessionId: metadata.sessionId,
1282
1308
  actorId: metadata.actorId,
1283
1309
  workflowId: metadata.workflowId,
1310
+ rootWorkflowId: metadata.rootWorkflowId,
1284
1311
  parentExecutionId: metadata.parentExecutionId,
1312
+ reasonerId: metadata.reasonerId,
1285
1313
  callerDid: metadata.callerDid,
1286
1314
  targetDid: metadata.targetDid,
1287
1315
  agentNodeDid: metadata.agentNodeDid,
1288
1316
  req,
1289
1317
  res,
1290
1318
  agent,
1319
+ logger: agent.getExecutionLogger(),
1291
1320
  aiClient: agent.getAIClient(),
1292
1321
  memory: agent.getMemoryInterface(metadata),
1293
1322
  workflow: agent.getWorkflowReporter(metadata),
@@ -1301,11 +1330,14 @@ var SkillContext = class {
1301
1330
  executionId;
1302
1331
  sessionId;
1303
1332
  workflowId;
1333
+ rootWorkflowId;
1334
+ reasonerId;
1304
1335
  callerDid;
1305
1336
  agentNodeDid;
1306
1337
  req;
1307
1338
  res;
1308
1339
  agent;
1340
+ logger;
1309
1341
  memory;
1310
1342
  workflow;
1311
1343
  did;
@@ -1314,11 +1346,14 @@ var SkillContext = class {
1314
1346
  this.executionId = params.executionId;
1315
1347
  this.sessionId = params.sessionId;
1316
1348
  this.workflowId = params.workflowId;
1349
+ this.rootWorkflowId = params.rootWorkflowId;
1350
+ this.reasonerId = params.reasonerId;
1317
1351
  this.callerDid = params.callerDid;
1318
1352
  this.agentNodeDid = params.agentNodeDid;
1319
1353
  this.req = params.req;
1320
1354
  this.res = params.res;
1321
1355
  this.agent = params.agent;
1356
+ this.logger = params.logger;
1322
1357
  this.memory = params.memory;
1323
1358
  this.workflow = params.workflow;
1324
1359
  this.did = params.did;
@@ -1336,11 +1371,14 @@ function getCurrentSkillContext() {
1336
1371
  executionId: metadata.executionId,
1337
1372
  sessionId: metadata.sessionId,
1338
1373
  workflowId: metadata.workflowId,
1374
+ rootWorkflowId: metadata.rootWorkflowId,
1375
+ reasonerId: metadata.reasonerId,
1339
1376
  callerDid: metadata.callerDid,
1340
1377
  agentNodeDid: metadata.agentNodeDid,
1341
1378
  req,
1342
1379
  res,
1343
1380
  agent,
1381
+ logger: agent.getExecutionLogger(),
1344
1382
  memory: agent.getMemoryInterface(metadata),
1345
1383
  workflow: agent.getWorkflowReporter(metadata),
1346
1384
  did: agent.getDidInterface(metadata, input)
@@ -1478,7 +1516,7 @@ var StatelessRateLimiter = class {
1478
1516
  }
1479
1517
  }
1480
1518
  async _sleep(delaySeconds) {
1481
- await new Promise((resolve) => setTimeout(resolve, delaySeconds * 1e3));
1519
+ await new Promise((resolve2) => setTimeout(resolve2, delaySeconds * 1e3));
1482
1520
  }
1483
1521
  _now() {
1484
1522
  return Date.now() / 1e3;
@@ -1517,8 +1555,8 @@ var StatelessRateLimiter = class {
1517
1555
  };
1518
1556
 
1519
1557
  // src/ai/AIClient.ts
1520
- function repairJsonText(text) {
1521
- let cleaned = text.trim();
1558
+ function repairJsonText(text2) {
1559
+ let cleaned = text2.trim();
1522
1560
  const codeBlockMatch = cleaned.match(/```(?:json)?\s*([\s\S]*?)```/);
1523
1561
  if (codeBlockMatch) {
1524
1562
  cleaned = codeBlockMatch[1].trim();
@@ -1564,7 +1602,7 @@ var AIClient = class {
1564
1602
  temperature: options.temperature ?? this.config.temperature,
1565
1603
  maxOutputTokens: options.maxTokens ?? this.config.maxTokens,
1566
1604
  schema,
1567
- experimental_repairText: async ({ text }) => repairJsonText(text)
1605
+ experimental_repairText: async ({ text: text2 }) => repairJsonText(text2)
1568
1606
  });
1569
1607
  const response2 = await this.withRateLimitRetry(call2);
1570
1608
  return response2.object;
@@ -1756,6 +1794,131 @@ var AIClient = class {
1756
1794
  return this.getRateLimiter().executeWithRetry(fn);
1757
1795
  }
1758
1796
  };
1797
+
1798
+ // src/observability/ExecutionLogger.ts
1799
+ function isExecutionLogBatchPayload(payload) {
1800
+ return "entries" in payload;
1801
+ }
1802
+ function safeJsonStringify(value) {
1803
+ const seen = /* @__PURE__ */ new WeakSet();
1804
+ return JSON.stringify(value, (_key, current) => {
1805
+ if (typeof current === "bigint") {
1806
+ return current.toString();
1807
+ }
1808
+ if (typeof current === "object" && current !== null) {
1809
+ if (seen.has(current)) {
1810
+ return "[Circular]";
1811
+ }
1812
+ seen.add(current);
1813
+ }
1814
+ return current;
1815
+ });
1816
+ }
1817
+ function mergeAttributes(existing, next) {
1818
+ if (!next) {
1819
+ return void 0;
1820
+ }
1821
+ return {
1822
+ ...{},
1823
+ ...next ?? {}
1824
+ };
1825
+ }
1826
+ function normalizeExecutionLogEntry(entry) {
1827
+ return {
1828
+ v: entry.v,
1829
+ ts: entry.ts,
1830
+ execution_id: entry.executionId,
1831
+ run_id: entry.runId,
1832
+ workflow_id: entry.workflowId,
1833
+ root_workflow_id: entry.rootWorkflowId,
1834
+ parent_execution_id: entry.parentExecutionId,
1835
+ session_id: entry.sessionId,
1836
+ actor_id: entry.actorId,
1837
+ agent_node_id: entry.agentNodeId,
1838
+ reasoner_id: entry.reasonerId,
1839
+ caller_did: entry.callerDid,
1840
+ target_did: entry.targetDid,
1841
+ agent_node_did: entry.agentNodeDid,
1842
+ level: entry.level,
1843
+ source: entry.source,
1844
+ event_type: entry.eventType,
1845
+ message: entry.message,
1846
+ attributes: entry.attributes,
1847
+ system_generated: entry.systemGenerated
1848
+ };
1849
+ }
1850
+ function serializeExecutionLogEntry(entry) {
1851
+ return safeJsonStringify(normalizeExecutionLogEntry(entry));
1852
+ }
1853
+ var ExecutionLogger = class {
1854
+ contextProvider;
1855
+ transport;
1856
+ mirrorToStdout;
1857
+ stdout;
1858
+ defaultSource;
1859
+ constructor(options = {}) {
1860
+ this.contextProvider = options.contextProvider;
1861
+ this.transport = options.transport;
1862
+ this.mirrorToStdout = options.mirrorToStdout ?? true;
1863
+ this.stdout = options.stdout ?? (typeof process !== "undefined" ? process.stdout : void 0);
1864
+ this.defaultSource = options.source ?? "sdk.logger";
1865
+ }
1866
+ log(level, message, attributes, options = {}) {
1867
+ const context = this.contextProvider?.() ?? {};
1868
+ const entry = {
1869
+ v: 1,
1870
+ ts: (/* @__PURE__ */ new Date()).toISOString(),
1871
+ level,
1872
+ source: options.source ?? this.defaultSource,
1873
+ message,
1874
+ ...context,
1875
+ ...options.eventType ? { eventType: options.eventType } : {},
1876
+ ...options.systemGenerated ? { systemGenerated: true } : {},
1877
+ ...attributes ? { attributes: mergeAttributes(void 0, attributes) } : {}
1878
+ };
1879
+ this.emit(entry);
1880
+ return entry;
1881
+ }
1882
+ debug(message, attributes, options) {
1883
+ return this.log("debug", message, attributes, options);
1884
+ }
1885
+ info(message, attributes, options) {
1886
+ return this.log("info", message, attributes, options);
1887
+ }
1888
+ warn(message, attributes, options) {
1889
+ return this.log("warn", message, attributes, options);
1890
+ }
1891
+ error(message, attributes, options) {
1892
+ return this.log("error", message, attributes, options);
1893
+ }
1894
+ system(eventType, message, attributes) {
1895
+ return this.log("info", message, attributes, {
1896
+ eventType,
1897
+ source: "sdk.runtime",
1898
+ systemGenerated: true
1899
+ });
1900
+ }
1901
+ emit(entry) {
1902
+ const wire = normalizeExecutionLogEntry(entry);
1903
+ const line = safeJsonStringify(wire) + "\n";
1904
+ if (this.mirrorToStdout && this.stdout?.write) {
1905
+ this.stdout.write(line);
1906
+ }
1907
+ if (this.transport && wire.execution_id) {
1908
+ try {
1909
+ const result = this.transport.emit(wire);
1910
+ if (result && typeof result.catch === "function") {
1911
+ void Promise.resolve(result).catch(() => {
1912
+ });
1913
+ }
1914
+ } catch {
1915
+ }
1916
+ }
1917
+ }
1918
+ };
1919
+ function createExecutionLogger(options = {}) {
1920
+ return new ExecutionLogger(options);
1921
+ }
1759
1922
  var httpAgent = new http.Agent({
1760
1923
  keepAlive: true,
1761
1924
  maxSockets: 10,
@@ -1901,7 +2064,9 @@ var AgentFieldClient = class {
1901
2064
  const headers = {};
1902
2065
  if (metadata?.runId) headers["X-Run-ID"] = metadata.runId;
1903
2066
  if (metadata?.workflowId) headers["X-Workflow-ID"] = metadata.workflowId;
2067
+ if (metadata?.rootWorkflowId) headers["X-Root-Workflow-ID"] = metadata.rootWorkflowId;
1904
2068
  if (metadata?.parentExecutionId) headers["X-Parent-Execution-ID"] = metadata.parentExecutionId;
2069
+ if (metadata?.reasonerId) headers["X-Reasoner-ID"] = metadata.reasonerId;
1905
2070
  if (metadata?.sessionId) headers["X-Session-ID"] = metadata.sessionId;
1906
2071
  if (metadata?.actorId) headers["X-Actor-ID"] = metadata.actorId;
1907
2072
  if (metadata?.callerDid) headers["X-Caller-DID"] = metadata.callerDid;
@@ -1935,6 +2100,7 @@ var AgentFieldClient = class {
1935
2100
  execution_id: event.executionId,
1936
2101
  workflow_id: event.workflowId ?? event.runId,
1937
2102
  run_id: event.runId,
2103
+ root_workflow_id: event.rootWorkflowId ?? event.workflowId ?? event.runId,
1938
2104
  reasoner_id: event.reasonerId,
1939
2105
  type: event.reasonerId,
1940
2106
  agent_node_id: event.agentNodeId,
@@ -1955,6 +2121,19 @@ var AgentFieldClient = class {
1955
2121
  }).catch(() => {
1956
2122
  });
1957
2123
  }
2124
+ publishExecutionLogs(payload) {
2125
+ const executionId = isExecutionLogBatchPayload(payload) ? payload.entries[0]?.execution_id : payload.execution_id;
2126
+ if (!executionId) {
2127
+ return;
2128
+ }
2129
+ const bodyStr = JSON.stringify(payload);
2130
+ const authHeaders = this.didAuthenticator.signRequest(Buffer.from(bodyStr));
2131
+ this.http.post(`/api/v1/executions/${encodeURIComponent(executionId)}/logs`, bodyStr, {
2132
+ headers: this.mergeHeaders({ "Content-Type": "application/json", ...authHeaders }),
2133
+ timeout: this.config.devMode ? 1e3 : 5e3
2134
+ }).catch(() => {
2135
+ });
2136
+ }
1958
2137
  async updateExecutionStatus(executionId, update) {
1959
2138
  if (!executionId) {
1960
2139
  throw new Error("executionId is required to update workflow status");
@@ -2105,7 +2284,9 @@ var AgentFieldClient = class {
2105
2284
  if (metadata.sessionId) headers["x-session-id"] = metadata.sessionId;
2106
2285
  if (metadata.actorId) headers["x-actor-id"] = metadata.actorId;
2107
2286
  if (metadata.workflowId) headers["x-workflow-id"] = metadata.workflowId;
2287
+ if (metadata.rootWorkflowId) headers["x-root-workflow-id"] = metadata.rootWorkflowId;
2108
2288
  if (metadata.parentExecutionId) headers["x-parent-execution-id"] = metadata.parentExecutionId;
2289
+ if (metadata.reasonerId) headers["x-reasoner-id"] = metadata.reasonerId;
2109
2290
  if (metadata.callerDid) headers["x-caller-did"] = metadata.callerDid;
2110
2291
  if (metadata.targetDid) headers["x-target-did"] = metadata.targetDid;
2111
2292
  if (metadata.agentNodeDid) headers["x-agent-node-did"] = metadata.agentNodeDid;
@@ -2495,11 +2676,11 @@ var MemoryInterface = class _MemoryInterface {
2495
2676
  metadata: this.metadata
2496
2677
  });
2497
2678
  }
2498
- async embedText(text, options) {
2679
+ async embedText(text2, options) {
2499
2680
  if (!this.aiClient) {
2500
2681
  throw new Error("AI client not configured for embeddings");
2501
2682
  }
2502
- return this.aiClient.embed(text, options);
2683
+ return this.aiClient.embed(text2, options);
2503
2684
  }
2504
2685
  async embedTexts(texts, options) {
2505
2686
  if (!this.aiClient) {
@@ -2507,8 +2688,8 @@ var MemoryInterface = class _MemoryInterface {
2507
2688
  }
2508
2689
  return this.aiClient.embedMany(texts, options);
2509
2690
  }
2510
- async embedAndSet(key, text, metadata, scope = this.defaultScope, scopeId = this.defaultScopeId, embeddingOptions) {
2511
- const embedding = await this.embedText(text, embeddingOptions);
2691
+ async embedAndSet(key, text2, metadata, scope = this.defaultScope, scopeId = this.defaultScopeId, embeddingOptions) {
2692
+ const embedding = await this.embedText(text2, embeddingOptions);
2512
2693
  await this.setVector(key, embedding, metadata, scope, scopeId);
2513
2694
  return embedding;
2514
2695
  }
@@ -3402,6 +3583,162 @@ function evaluateConstraints(constraints, inputParams) {
3402
3583
  return true;
3403
3584
  }
3404
3585
 
3586
+ // src/agent/processLogs.ts
3587
+ function logsEnabled() {
3588
+ const v = (process.env.AGENTFIELD_LOGS_ENABLED ?? "true").trim().toLowerCase();
3589
+ return !["0", "false", "no", "off"].includes(v);
3590
+ }
3591
+ function maxBufferBytes() {
3592
+ const raw = parseInt(process.env.AGENTFIELD_LOG_BUFFER_BYTES ?? "4194304", 10);
3593
+ return Number.isFinite(raw) && raw >= 1024 ? raw : 4194304;
3594
+ }
3595
+ function maxLineBytes() {
3596
+ const raw = parseInt(process.env.AGENTFIELD_LOG_MAX_LINE_BYTES ?? "16384", 10);
3597
+ return Number.isFinite(raw) && raw >= 256 ? raw : 16384;
3598
+ }
3599
+ function maxTailLines() {
3600
+ const raw = parseInt(process.env.AGENTFIELD_LOG_MAX_TAIL_LINES ?? "50000", 10);
3601
+ return Number.isFinite(raw) && raw >= 1 ? raw : 5e4;
3602
+ }
3603
+ function internalBearerOk(authHeader) {
3604
+ const want = (process.env.AGENTFIELD_AUTHORIZATION_INTERNAL_TOKEN ?? "").trim();
3605
+ if (!want) return true;
3606
+ if (!authHeader?.toLowerCase().startsWith("bearer ")) return false;
3607
+ return authHeader.slice(7).trim() === want;
3608
+ }
3609
+ var ProcessLogRing = class {
3610
+ seq = 0;
3611
+ entries = [];
3612
+ approxBytes = 0;
3613
+ maxBytes;
3614
+ constructor() {
3615
+ this.maxBytes = maxBufferBytes();
3616
+ }
3617
+ append(stream, line, truncated) {
3618
+ const ts = (/* @__PURE__ */ new Date()).toISOString();
3619
+ this.seq += 1;
3620
+ const sl = stream.toLowerCase();
3621
+ const level = sl === "stderr" ? "error" : sl === "stdout" ? "info" : "log";
3622
+ const e = {
3623
+ v: 1,
3624
+ seq: this.seq,
3625
+ ts,
3626
+ stream,
3627
+ line,
3628
+ level,
3629
+ source: "process",
3630
+ truncated
3631
+ };
3632
+ this.entries.push(e);
3633
+ this.approxBytes += line.length + 64;
3634
+ while (this.approxBytes > this.maxBytes && this.entries.length > 1) {
3635
+ const old = this.entries.shift();
3636
+ this.approxBytes -= old.line.length + 64;
3637
+ }
3638
+ }
3639
+ tail(n) {
3640
+ if (n <= 0) return [];
3641
+ return this.entries.length <= n ? [...this.entries] : this.entries.slice(-n);
3642
+ }
3643
+ snapshotAfter(sinceSeq, limit) {
3644
+ const buf = this.entries.filter((e) => e.seq > sinceSeq);
3645
+ if (limit != null && limit > 0 && buf.length > limit) {
3646
+ return buf.slice(-limit);
3647
+ }
3648
+ return buf;
3649
+ }
3650
+ };
3651
+ var captureInstalled = false;
3652
+ function installStdioLogCapture(ring) {
3653
+ if (captureInstalled || !logsEnabled()) return;
3654
+ captureInstalled = true;
3655
+ const maxLB = maxLineBytes();
3656
+ const hook = (stream, name) => {
3657
+ const orig = stream.write.bind(stream);
3658
+ let buf = "";
3659
+ stream.write = (chunk, ...args) => {
3660
+ const s = typeof chunk === "string" ? chunk : Buffer.isBuffer(chunk) ? chunk.toString("utf8") : String(chunk);
3661
+ buf += s;
3662
+ let idx;
3663
+ while ((idx = buf.indexOf("\n")) >= 0) {
3664
+ const line = buf.slice(0, idx);
3665
+ buf = buf.slice(idx + 1);
3666
+ let out = line;
3667
+ let trunc = false;
3668
+ if (Buffer.byteLength(out, "utf8") > maxLB) {
3669
+ out = Buffer.from(out, "utf8").subarray(0, maxLB).toString("utf8");
3670
+ trunc = true;
3671
+ }
3672
+ ring.append(name, out, trunc);
3673
+ }
3674
+ return orig(chunk, ...args);
3675
+ };
3676
+ };
3677
+ hook(process.stdout, "stdout");
3678
+ hook(process.stderr, "stderr");
3679
+ }
3680
+ function registerAgentfieldLogsRoute(app, ring) {
3681
+ app.get("/agentfield/v1/logs", (req, res) => {
3682
+ if (!logsEnabled()) {
3683
+ return res.status(404).json({
3684
+ error: "logs_disabled",
3685
+ message: "Process logs API is disabled"
3686
+ });
3687
+ }
3688
+ const auth = req.headers.authorization;
3689
+ if (!internalBearerOk(auth)) {
3690
+ return res.status(401).json({
3691
+ error: "unauthorized",
3692
+ message: "Valid Authorization Bearer required"
3693
+ });
3694
+ }
3695
+ let tailLines = parseInt(String(req.query.tail_lines ?? "0"), 10);
3696
+ const sinceSeq = parseInt(String(req.query.since_seq ?? "0"), 10);
3697
+ const follow = ["1", "true", "yes"].includes(String(req.query.follow ?? "").toLowerCase());
3698
+ const cap = maxTailLines();
3699
+ if (tailLines > cap) {
3700
+ return res.status(413).json({
3701
+ error: "tail_too_large",
3702
+ message: `tail_lines exceeds max ${cap}`
3703
+ });
3704
+ }
3705
+ if (tailLines <= 0 && sinceSeq <= 0 && !follow) tailLines = 200;
3706
+ let initial;
3707
+ if (sinceSeq > 0) {
3708
+ initial = ring.snapshotAfter(sinceSeq, tailLines > 0 ? tailLines : null);
3709
+ } else {
3710
+ const n = tailLines > 0 ? tailLines : 200;
3711
+ initial = ring.tail(n);
3712
+ }
3713
+ res.setHeader("Content-Type", "application/x-ndjson");
3714
+ res.setHeader("Cache-Control", "no-store");
3715
+ res.status(200);
3716
+ const writeLines = (entries) => {
3717
+ for (const e of entries) {
3718
+ res.write(`${JSON.stringify(e)}
3719
+ `);
3720
+ }
3721
+ res.flush?.();
3722
+ };
3723
+ writeLines(initial);
3724
+ let lastSeq = sinceSeq;
3725
+ if (initial.length) lastSeq = initial[initial.length - 1].seq;
3726
+ if (!follow) {
3727
+ return res.end();
3728
+ }
3729
+ const iv = setInterval(() => {
3730
+ const newer = ring.snapshotAfter(lastSeq, null);
3731
+ if (newer.length) {
3732
+ writeLines(newer);
3733
+ lastSeq = newer[newer.length - 1].seq;
3734
+ }
3735
+ }, 400);
3736
+ req.on("close", () => {
3737
+ clearInterval(iv);
3738
+ });
3739
+ });
3740
+ }
3741
+
3405
3742
  // src/agent/Agent.ts
3406
3743
  var TargetNotFoundError = class extends Error {
3407
3744
  };
@@ -3424,6 +3761,8 @@ var Agent = class {
3424
3761
  mcpToolRegistrar;
3425
3762
  localVerifier;
3426
3763
  realtimeValidationFunctions = /* @__PURE__ */ new Set();
3764
+ processLogRing = new ProcessLogRing();
3765
+ executionLogger;
3427
3766
  constructor(config) {
3428
3767
  const mcp = config.mcp ? {
3429
3768
  autoRegisterTools: config.mcp.autoRegisterTools ?? true,
@@ -3446,6 +3785,12 @@ var Agent = class {
3446
3785
  this.memoryEventClient = new MemoryEventClient(this.config.agentFieldUrl, this.config.defaultHeaders);
3447
3786
  this.didClient = new DidClient(this.config.agentFieldUrl, this.config.defaultHeaders);
3448
3787
  this.didManager = new DidManager(this.didClient, this.config.nodeId);
3788
+ this.executionLogger = createExecutionLogger({
3789
+ contextProvider: () => this.buildExecutionLogContext(),
3790
+ transport: {
3791
+ emit: (payload) => this.agentFieldClient.publishExecutionLogs(payload)
3792
+ }
3793
+ });
3449
3794
  this.memoryEventClient.onEvent((event) => this.dispatchMemoryEvent(event));
3450
3795
  if (this.config.mcp?.servers?.length) {
3451
3796
  this.mcpClientRegistry = new MCPClientRegistry(this.config.devMode);
@@ -3465,6 +3810,8 @@ var Agent = class {
3465
3810
  );
3466
3811
  }
3467
3812
  this.registerDefaultRoutes();
3813
+ installStdioLogCapture(this.processLogRing);
3814
+ registerAgentfieldLogsRoute(this.app, this.processLogRing);
3468
3815
  }
3469
3816
  reasoner(name, handler, options) {
3470
3817
  this.reasoners.register(name, handler, options);
@@ -3510,6 +3857,9 @@ var Agent = class {
3510
3857
  getAIClient() {
3511
3858
  return this.aiClient;
3512
3859
  }
3860
+ getExecutionLogger() {
3861
+ return this.executionLogger;
3862
+ }
3513
3863
  async getHarnessRunner() {
3514
3864
  const cached = harnessRunners.get(this);
3515
3865
  if (cached) return cached;
@@ -3550,7 +3900,8 @@ var Agent = class {
3550
3900
  executionId: metadata.executionId,
3551
3901
  runId: metadata.runId,
3552
3902
  workflowId: metadata.workflowId,
3553
- agentNodeId: this.config.nodeId
3903
+ agentNodeId: this.config.nodeId,
3904
+ reasonerId: metadata.reasonerId
3554
3905
  });
3555
3906
  }
3556
3907
  getDidInterface(metadata, defaultInput, targetName) {
@@ -3580,6 +3931,24 @@ var Agent = class {
3580
3931
  }
3581
3932
  this.agentFieldClient.sendNote(message, tags, this.config.nodeId, execMetadata, uiApiUrl, this.config.devMode);
3582
3933
  }
3934
+ buildExecutionLogContext(metadata) {
3935
+ const current = metadata ?? ExecutionContext.getCurrent()?.metadata;
3936
+ if (!current) return void 0;
3937
+ return {
3938
+ executionId: current.executionId,
3939
+ runId: current.runId,
3940
+ workflowId: current.workflowId,
3941
+ rootWorkflowId: current.rootWorkflowId ?? current.workflowId ?? current.runId ?? current.executionId,
3942
+ parentExecutionId: current.parentExecutionId,
3943
+ sessionId: current.sessionId,
3944
+ actorId: current.actorId,
3945
+ agentNodeId: this.config.nodeId,
3946
+ reasonerId: current.reasonerId,
3947
+ callerDid: current.callerDid,
3948
+ targetDid: current.targetDid,
3949
+ agentNodeDid: current.agentNodeDid
3950
+ };
3951
+ }
3583
3952
  async serve() {
3584
3953
  if (this.config.mcp?.autoRegisterTools !== false) {
3585
3954
  try {
@@ -3604,8 +3973,8 @@ var Agent = class {
3604
3973
  const port = this.config.port ?? 8001;
3605
3974
  const host = this.config.host ?? "0.0.0.0";
3606
3975
  await this.agentFieldClient.heartbeat("starting");
3607
- await new Promise((resolve, reject) => {
3608
- this.server = this.app.listen(port, host, () => resolve()).on("error", reject);
3976
+ await new Promise((resolve2, reject) => {
3977
+ this.server = this.app.listen(port, host, () => resolve2()).on("error", reject);
3609
3978
  });
3610
3979
  this.memoryEventClient.start();
3611
3980
  this.startHeartbeat();
@@ -3614,46 +3983,59 @@ var Agent = class {
3614
3983
  if (this.heartbeatTimer) {
3615
3984
  clearInterval(this.heartbeatTimer);
3616
3985
  }
3617
- await new Promise((resolve, reject) => {
3986
+ await new Promise((resolve2, reject) => {
3618
3987
  this.server?.close((err) => {
3619
3988
  if (err) reject(err);
3620
- else resolve();
3989
+ else resolve2();
3621
3990
  });
3622
3991
  });
3623
3992
  this.memoryEventClient.stop();
3624
3993
  }
3625
3994
  async call(target, input) {
3626
3995
  const { agentId, name } = this.parseTarget(target);
3996
+ const parentMetadata = ExecutionContext.getCurrent()?.metadata;
3627
3997
  if (!agentId || agentId === this.config.nodeId) {
3628
3998
  const local = this.reasoners.get(name);
3629
3999
  if (!local) throw new Error(`Reasoner not found: ${name}`);
3630
- const parentMetadata = ExecutionContext.getCurrent()?.metadata;
3631
- const runId = parentMetadata?.runId ?? parentMetadata?.executionId ?? randomUUID();
3632
- const metadata2 = {
4000
+ const runId2 = parentMetadata?.runId ?? parentMetadata?.executionId ?? randomUUID();
4001
+ const rootWorkflowId2 = parentMetadata?.rootWorkflowId ?? parentMetadata?.workflowId ?? runId2;
4002
+ const metadata = {
3633
4003
  ...parentMetadata,
3634
4004
  executionId: randomUUID(),
3635
4005
  parentExecutionId: parentMetadata?.executionId,
3636
- runId,
3637
- workflowId: parentMetadata?.workflowId ?? runId
4006
+ runId: runId2,
4007
+ workflowId: parentMetadata?.workflowId ?? runId2,
4008
+ rootWorkflowId: rootWorkflowId2,
4009
+ reasonerId: name
3638
4010
  };
3639
4011
  const dummyReq = {};
3640
4012
  const dummyRes = {};
3641
4013
  const execCtx = new ExecutionContext({
3642
4014
  input,
3643
4015
  metadata: {
3644
- ...metadata2,
3645
- executionId: metadata2.executionId ?? randomUUID()
4016
+ ...metadata,
4017
+ executionId: metadata.executionId ?? randomUUID()
3646
4018
  },
3647
4019
  req: dummyReq,
3648
4020
  res: dummyRes,
3649
4021
  agent: this
3650
4022
  });
3651
4023
  const startTime = Date.now();
4024
+ this.executionLogger.system("agent.call.started", "Local agent call started", {
4025
+ target,
4026
+ reasonerId: name,
4027
+ executionId: metadata.executionId,
4028
+ parentExecutionId: metadata.parentExecutionId,
4029
+ runId: metadata.runId,
4030
+ workflowId: metadata.workflowId,
4031
+ rootWorkflowId: metadata.rootWorkflowId
4032
+ });
3652
4033
  const emitEvent = async (status, payload) => {
3653
4034
  await this.agentFieldClient.publishWorkflowEvent({
3654
4035
  executionId: execCtx.metadata.executionId,
3655
4036
  runId: execCtx.metadata.runId ?? execCtx.metadata.executionId,
3656
4037
  workflowId: execCtx.metadata.workflowId,
4038
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
3657
4039
  reasonerId: name,
3658
4040
  agentNodeId: this.config.nodeId,
3659
4041
  status,
@@ -3667,6 +4049,22 @@ var Agent = class {
3667
4049
  };
3668
4050
  await emitEvent("running", null);
3669
4051
  return ExecutionContext.run(execCtx, async () => {
4052
+ this.executionLogger.system("execution.started", "Execution started", {
4053
+ target,
4054
+ reasonerId: name,
4055
+ executionId: execCtx.metadata.executionId,
4056
+ parentExecutionId: execCtx.metadata.parentExecutionId,
4057
+ runId: execCtx.metadata.runId,
4058
+ workflowId: execCtx.metadata.workflowId,
4059
+ rootWorkflowId: execCtx.metadata.rootWorkflowId
4060
+ });
4061
+ this.executionLogger.system("reasoner.started", "Reasoner execution started", {
4062
+ target: name,
4063
+ executionId: execCtx.metadata.executionId,
4064
+ runId: execCtx.metadata.runId,
4065
+ workflowId: execCtx.metadata.workflowId,
4066
+ rootWorkflowId: execCtx.metadata.rootWorkflowId
4067
+ });
3670
4068
  try {
3671
4069
  const result = await local.handler(
3672
4070
  new ReasonerContext({
@@ -3676,39 +4074,154 @@ var Agent = class {
3676
4074
  sessionId: execCtx.metadata.sessionId,
3677
4075
  actorId: execCtx.metadata.actorId,
3678
4076
  workflowId: execCtx.metadata.workflowId,
4077
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
3679
4078
  parentExecutionId: execCtx.metadata.parentExecutionId,
4079
+ reasonerId: name,
3680
4080
  callerDid: execCtx.metadata.callerDid,
3681
4081
  targetDid: execCtx.metadata.targetDid,
3682
4082
  agentNodeDid: execCtx.metadata.agentNodeDid,
3683
4083
  req: dummyReq,
3684
4084
  res: dummyRes,
3685
4085
  agent: this,
4086
+ logger: this.executionLogger,
3686
4087
  aiClient: this.aiClient,
3687
4088
  memory: this.getMemoryInterface(execCtx.metadata),
3688
4089
  workflow: this.getWorkflowReporter(execCtx.metadata),
3689
4090
  did: this.getDidInterface(execCtx.metadata, input, name)
3690
4091
  })
3691
4092
  );
4093
+ this.executionLogger.system("reasoner.completed", "Reasoner execution completed", {
4094
+ target: name,
4095
+ executionId: execCtx.metadata.executionId,
4096
+ runId: execCtx.metadata.runId,
4097
+ workflowId: execCtx.metadata.workflowId,
4098
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4099
+ durationMs: Date.now() - startTime
4100
+ });
4101
+ this.executionLogger.system("execution.completed", "Execution completed", {
4102
+ target,
4103
+ reasonerId: name,
4104
+ executionId: execCtx.metadata.executionId,
4105
+ runId: execCtx.metadata.runId,
4106
+ workflowId: execCtx.metadata.workflowId,
4107
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4108
+ durationMs: Date.now() - startTime
4109
+ });
4110
+ this.executionLogger.system("agent.call.completed", "Local agent call completed", {
4111
+ target,
4112
+ reasonerId: name,
4113
+ executionId: execCtx.metadata.executionId,
4114
+ runId: execCtx.metadata.runId,
4115
+ workflowId: execCtx.metadata.workflowId,
4116
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4117
+ durationMs: Date.now() - startTime
4118
+ });
3692
4119
  await emitEvent("succeeded", result);
3693
4120
  return result;
3694
4121
  } catch (err) {
4122
+ this.executionLogger.error("Reasoner execution failed", {
4123
+ target: name,
4124
+ executionId: execCtx.metadata.executionId,
4125
+ runId: execCtx.metadata.runId,
4126
+ workflowId: execCtx.metadata.workflowId,
4127
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4128
+ durationMs: Date.now() - startTime,
4129
+ error: err instanceof Error ? err.message : String(err)
4130
+ }, {
4131
+ eventType: "reasoner.failed",
4132
+ source: "sdk.runtime",
4133
+ systemGenerated: true
4134
+ });
4135
+ this.executionLogger.error("Execution failed", {
4136
+ target,
4137
+ reasonerId: name,
4138
+ executionId: execCtx.metadata.executionId,
4139
+ runId: execCtx.metadata.runId,
4140
+ workflowId: execCtx.metadata.workflowId,
4141
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4142
+ durationMs: Date.now() - startTime,
4143
+ error: err instanceof Error ? err.message : String(err)
4144
+ }, {
4145
+ eventType: "execution.failed",
4146
+ source: "sdk.runtime",
4147
+ systemGenerated: true
4148
+ });
4149
+ this.executionLogger.error("Local agent call failed", {
4150
+ target,
4151
+ reasonerId: name,
4152
+ executionId: execCtx.metadata.executionId,
4153
+ runId: execCtx.metadata.runId,
4154
+ workflowId: execCtx.metadata.workflowId,
4155
+ rootWorkflowId: execCtx.metadata.rootWorkflowId,
4156
+ durationMs: Date.now() - startTime,
4157
+ error: err instanceof Error ? err.message : String(err)
4158
+ }, {
4159
+ eventType: "agent.call.failed",
4160
+ source: "sdk.runtime",
4161
+ systemGenerated: true
4162
+ });
3695
4163
  await emitEvent("failed", err);
3696
4164
  throw err;
3697
4165
  }
3698
4166
  });
3699
4167
  }
3700
- const metadata = ExecutionContext.getCurrent()?.metadata;
3701
- return this.agentFieldClient.execute(target, input, {
3702
- runId: metadata?.runId ?? metadata?.executionId,
3703
- workflowId: metadata?.workflowId ?? metadata?.runId,
3704
- parentExecutionId: metadata?.executionId,
3705
- sessionId: metadata?.sessionId,
3706
- actorId: metadata?.actorId,
3707
- callerDid: metadata?.callerDid,
3708
- targetDid: metadata?.targetDid,
3709
- agentNodeDid: metadata?.agentNodeDid,
3710
- agentNodeId: this.config.nodeId
4168
+ const executionId = parentMetadata?.executionId ?? randomUUID();
4169
+ const runId = parentMetadata?.runId ?? parentMetadata?.executionId ?? executionId;
4170
+ const workflowId = parentMetadata?.workflowId ?? runId;
4171
+ const rootWorkflowId = parentMetadata?.rootWorkflowId ?? workflowId;
4172
+ this.executionLogger.system("agent.call.started", "Remote agent call started", {
4173
+ target,
4174
+ agentNodeId: agentId,
4175
+ executionId,
4176
+ parentExecutionId: parentMetadata?.executionId,
4177
+ runId,
4178
+ workflowId,
4179
+ rootWorkflowId,
4180
+ reasonerId: name
3711
4181
  });
4182
+ try {
4183
+ const result = await this.agentFieldClient.execute(target, input, {
4184
+ runId,
4185
+ workflowId,
4186
+ rootWorkflowId,
4187
+ parentExecutionId: parentMetadata?.executionId,
4188
+ reasonerId: name,
4189
+ sessionId: parentMetadata?.sessionId,
4190
+ actorId: parentMetadata?.actorId,
4191
+ callerDid: parentMetadata?.callerDid,
4192
+ targetDid: parentMetadata?.targetDid,
4193
+ agentNodeDid: parentMetadata?.agentNodeDid,
4194
+ agentNodeId: this.config.nodeId
4195
+ });
4196
+ this.executionLogger.system("agent.call.completed", "Remote agent call completed", {
4197
+ target,
4198
+ agentNodeId: agentId,
4199
+ executionId,
4200
+ parentExecutionId: parentMetadata?.executionId,
4201
+ runId,
4202
+ workflowId,
4203
+ rootWorkflowId,
4204
+ reasonerId: name
4205
+ });
4206
+ return result;
4207
+ } catch (err) {
4208
+ this.executionLogger.error("Remote agent call failed", {
4209
+ target,
4210
+ agentNodeId: agentId,
4211
+ executionId,
4212
+ parentExecutionId: parentMetadata?.executionId,
4213
+ runId,
4214
+ workflowId,
4215
+ rootWorkflowId,
4216
+ reasonerId: name,
4217
+ error: err instanceof Error ? err.message : String(err)
4218
+ }, {
4219
+ eventType: "agent.call.failed",
4220
+ source: "sdk.runtime",
4221
+ systemGenerated: true
4222
+ });
4223
+ throw err;
4224
+ }
3712
4225
  }
3713
4226
  registerDefaultRoutes() {
3714
4227
  this.app.get("/health", (_req, res) => {
@@ -3762,22 +4275,22 @@ var Agent = class {
3762
4275
  },
3763
4276
  message: { error: "rate_limit_exceeded", message: "Too many authentication attempts. Try again later." },
3764
4277
  skip: (req) => {
3765
- const path2 = req.path;
3766
- if (!path2.startsWith("/reasoners/") && !path2.startsWith("/skills/") && !path2.startsWith("/execute") && !path2.startsWith("/api/v1/reasoners/") && !path2.startsWith("/api/v1/skills/")) {
4278
+ const path3 = req.path;
4279
+ if (!path3.startsWith("/reasoners/") && !path3.startsWith("/skills/") && !path3.startsWith("/execute") && !path3.startsWith("/api/v1/reasoners/") && !path3.startsWith("/api/v1/skills/")) {
3767
4280
  return true;
3768
4281
  }
3769
- const parts = path2.replace(/^\/+/, "").split("/");
4282
+ const parts = path3.replace(/^\/+/, "").split("/");
3770
4283
  const funcName = parts[parts.length - 1] ?? "";
3771
4284
  return realtimeFunctions.has(funcName);
3772
4285
  }
3773
4286
  });
3774
4287
  this.app.use(authRateLimiter);
3775
4288
  this.app.use(async (req, res, next) => {
3776
- const path2 = req.path;
3777
- if (!path2.startsWith("/reasoners/") && !path2.startsWith("/skills/") && !path2.startsWith("/execute") && !path2.startsWith("/api/v1/reasoners/") && !path2.startsWith("/api/v1/skills/")) {
4289
+ const path3 = req.path;
4290
+ if (!path3.startsWith("/reasoners/") && !path3.startsWith("/skills/") && !path3.startsWith("/execute") && !path3.startsWith("/api/v1/reasoners/") && !path3.startsWith("/api/v1/skills/")) {
3778
4291
  return next();
3779
4292
  }
3780
- const parts = path2.replace(/^\/+/, "").split("/");
4293
+ const parts = path3.replace(/^\/+/, "").split("/");
3781
4294
  const funcName = parts[parts.length - 1] ?? "";
3782
4295
  if (realtimeFunctions.has(funcName)) {
3783
4296
  return next();
@@ -3947,13 +4460,16 @@ var Agent = class {
3947
4460
  const executionId = overrides?.executionId ?? normalized["x-execution-id"] ?? randomUUID();
3948
4461
  const runId = overrides?.runId ?? normalized["x-run-id"] ?? executionId;
3949
4462
  const workflowId = overrides?.workflowId ?? normalized["x-workflow-id"] ?? runId;
4463
+ const rootWorkflowId = overrides?.rootWorkflowId ?? normalized["x-root-workflow-id"] ?? workflowId;
3950
4464
  return {
3951
4465
  executionId,
3952
4466
  runId,
3953
4467
  workflowId,
4468
+ rootWorkflowId,
3954
4469
  sessionId: overrides?.sessionId ?? normalized["x-session-id"],
3955
4470
  actorId: overrides?.actorId ?? normalized["x-actor-id"],
3956
4471
  parentExecutionId: overrides?.parentExecutionId ?? normalized["x-parent-execution-id"],
4472
+ reasonerId: overrides?.reasonerId ?? normalized["x-reasoner-id"],
3957
4473
  callerDid: overrides?.callerDid ?? normalized["x-caller-did"],
3958
4474
  targetDid: overrides?.targetDid ?? normalized["x-target-did"],
3959
4475
  agentNodeDid: overrides?.agentNodeDid ?? normalized["x-agent-node-did"] ?? normalized["x-agent-did"]
@@ -3964,9 +4480,9 @@ var Agent = class {
3964
4480
  return handler(req, res);
3965
4481
  }
3966
4482
  async handleServerlessEvent(event) {
3967
- const path2 = event?.path ?? event?.rawPath ?? "";
4483
+ const path3 = event?.path ?? event?.rawPath ?? "";
3968
4484
  const action = event?.action ?? "";
3969
- if (path2 === "/discover" || action === "discover") {
4485
+ if (path3 === "/discover" || action === "discover") {
3970
4486
  return {
3971
4487
  statusCode: 200,
3972
4488
  headers: { "content-type": "application/json" },
@@ -3975,7 +4491,7 @@ var Agent = class {
3975
4491
  }
3976
4492
  const body = this.normalizeEventBody(event);
3977
4493
  const invocation = this.extractInvocationDetails({
3978
- path: path2,
4494
+ path: path3,
3979
4495
  query: event?.queryStringParameters,
3980
4496
  body,
3981
4497
  reasoner: event?.reasoner,
@@ -4031,7 +4547,9 @@ var Agent = class {
4031
4547
  executionId: ctx.executionId ?? ctx.execution_id ?? ctx.executionId,
4032
4548
  runId: ctx.runId ?? ctx.run_id,
4033
4549
  workflowId: ctx.workflowId ?? ctx.workflow_id,
4550
+ rootWorkflowId: ctx.rootWorkflowId ?? ctx.root_workflow_id,
4034
4551
  parentExecutionId: ctx.parentExecutionId ?? ctx.parent_execution_id,
4552
+ reasonerId: ctx.reasonerId ?? ctx.reasoner_id,
4035
4553
  sessionId: ctx.sessionId ?? ctx.session_id,
4036
4554
  actorId: ctx.actorId ?? ctx.actor_id,
4037
4555
  callerDid: ctx.callerDid ?? ctx.caller_did,
@@ -4065,9 +4583,9 @@ var Agent = class {
4065
4583
  const input = this.normalizeInputPayload(params.body);
4066
4584
  return { name: name ?? void 0, targetType: typeValue, input };
4067
4585
  }
4068
- parsePathTarget(path2) {
4069
- if (!path2) return {};
4070
- const normalized = path2.split("?")[0];
4586
+ parsePathTarget(path3) {
4587
+ if (!path3) return {};
4588
+ const normalized = path3.split("?")[0];
4071
4589
  const reasonerMatch = normalized.match(/\/reasoners\/([^/]+)/);
4072
4590
  if (reasonerMatch?.[1]) {
4073
4591
  return { name: reasonerMatch[1], targetType: "reasoner" };
@@ -4178,41 +4696,107 @@ var Agent = class {
4178
4696
  async runReasoner(reasoner, params) {
4179
4697
  const req = params.req ?? {};
4180
4698
  const res = params.res ?? {};
4699
+ const executionMetadata = {
4700
+ ...params.metadata,
4701
+ rootWorkflowId: params.metadata.rootWorkflowId ?? params.metadata.workflowId ?? params.metadata.runId ?? params.metadata.executionId,
4702
+ reasonerId: params.metadata.reasonerId ?? params.targetName
4703
+ };
4181
4704
  const execCtx = new ExecutionContext({
4182
4705
  input: params.input,
4183
- metadata: params.metadata,
4706
+ metadata: executionMetadata,
4184
4707
  req,
4185
4708
  res,
4186
4709
  agent: this
4187
4710
  });
4188
4711
  return ExecutionContext.run(execCtx, async () => {
4712
+ this.executionLogger.system("execution.started", "Execution started", {
4713
+ target: params.targetName,
4714
+ reasonerId: executionMetadata.reasonerId,
4715
+ executionId: executionMetadata.executionId,
4716
+ parentExecutionId: executionMetadata.parentExecutionId,
4717
+ runId: executionMetadata.runId,
4718
+ workflowId: executionMetadata.workflowId,
4719
+ rootWorkflowId: executionMetadata.rootWorkflowId
4720
+ });
4721
+ this.executionLogger.system("reasoner.started", "Reasoner execution started", {
4722
+ target: params.targetName,
4723
+ executionId: executionMetadata.executionId,
4724
+ runId: executionMetadata.runId,
4725
+ workflowId: executionMetadata.workflowId,
4726
+ rootWorkflowId: executionMetadata.rootWorkflowId
4727
+ });
4189
4728
  try {
4190
4729
  const ctx = new ReasonerContext({
4191
4730
  input: params.input,
4192
- executionId: params.metadata.executionId,
4193
- runId: params.metadata.runId,
4194
- sessionId: params.metadata.sessionId,
4195
- actorId: params.metadata.actorId,
4196
- workflowId: params.metadata.workflowId,
4197
- parentExecutionId: params.metadata.parentExecutionId,
4198
- callerDid: params.metadata.callerDid,
4199
- targetDid: params.metadata.targetDid,
4200
- agentNodeDid: params.metadata.agentNodeDid,
4731
+ executionId: executionMetadata.executionId,
4732
+ runId: executionMetadata.runId,
4733
+ sessionId: executionMetadata.sessionId,
4734
+ actorId: executionMetadata.actorId,
4735
+ workflowId: executionMetadata.workflowId,
4736
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4737
+ parentExecutionId: executionMetadata.parentExecutionId,
4738
+ reasonerId: executionMetadata.reasonerId,
4739
+ callerDid: executionMetadata.callerDid,
4740
+ targetDid: executionMetadata.targetDid,
4741
+ agentNodeDid: executionMetadata.agentNodeDid,
4201
4742
  req,
4202
4743
  res,
4203
4744
  agent: this,
4745
+ logger: this.executionLogger,
4204
4746
  aiClient: this.aiClient,
4205
- memory: this.getMemoryInterface(params.metadata),
4206
- workflow: this.getWorkflowReporter(params.metadata),
4207
- did: this.getDidInterface(params.metadata, params.input, params.targetName)
4747
+ memory: this.getMemoryInterface(executionMetadata),
4748
+ workflow: this.getWorkflowReporter(executionMetadata),
4749
+ did: this.getDidInterface(executionMetadata, params.input, params.targetName)
4208
4750
  });
4209
4751
  const result = await reasoner.handler(ctx);
4752
+ this.executionLogger.system("reasoner.completed", "Reasoner execution completed", {
4753
+ target: params.targetName,
4754
+ executionId: executionMetadata.executionId,
4755
+ runId: executionMetadata.runId,
4756
+ workflowId: executionMetadata.workflowId,
4757
+ rootWorkflowId: executionMetadata.rootWorkflowId
4758
+ });
4759
+ this.executionLogger.system("execution.completed", "Execution completed", {
4760
+ target: params.targetName,
4761
+ reasonerId: executionMetadata.reasonerId,
4762
+ executionId: executionMetadata.executionId,
4763
+ runId: executionMetadata.runId,
4764
+ workflowId: executionMetadata.workflowId,
4765
+ rootWorkflowId: executionMetadata.rootWorkflowId
4766
+ });
4210
4767
  if (params.respond && params.res) {
4211
4768
  params.res.json(result);
4212
4769
  return;
4213
4770
  }
4214
4771
  return result;
4215
4772
  } catch (err) {
4773
+ this.executionLogger.error("Reasoner execution failed", {
4774
+ target: params.targetName,
4775
+ executionId: executionMetadata.executionId,
4776
+ parentExecutionId: executionMetadata.parentExecutionId,
4777
+ runId: executionMetadata.runId,
4778
+ workflowId: executionMetadata.workflowId,
4779
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4780
+ error: err?.message ?? "Execution failed"
4781
+ }, {
4782
+ eventType: "reasoner.failed",
4783
+ source: "sdk.runtime",
4784
+ systemGenerated: true
4785
+ });
4786
+ this.executionLogger.error("Execution failed", {
4787
+ target: params.targetName,
4788
+ reasonerId: executionMetadata.reasonerId,
4789
+ executionId: executionMetadata.executionId,
4790
+ parentExecutionId: executionMetadata.parentExecutionId,
4791
+ runId: executionMetadata.runId,
4792
+ workflowId: executionMetadata.workflowId,
4793
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4794
+ error: err?.message ?? "Execution failed"
4795
+ }, {
4796
+ eventType: "execution.failed",
4797
+ source: "sdk.runtime",
4798
+ systemGenerated: true
4799
+ });
4216
4800
  if (params.respond && params.res) {
4217
4801
  const body = { error: err?.message ?? "Execution failed" };
4218
4802
  if (err?.responseData) body.error_details = err.responseData;
@@ -4227,34 +4811,100 @@ var Agent = class {
4227
4811
  async runSkill(skill, params) {
4228
4812
  const req = params.req ?? {};
4229
4813
  const res = params.res ?? {};
4814
+ const executionMetadata = {
4815
+ ...params.metadata,
4816
+ rootWorkflowId: params.metadata.rootWorkflowId ?? params.metadata.workflowId ?? params.metadata.runId ?? params.metadata.executionId,
4817
+ reasonerId: params.metadata.reasonerId ?? params.targetName
4818
+ };
4230
4819
  const execCtx = new ExecutionContext({
4231
4820
  input: params.input,
4232
- metadata: params.metadata,
4821
+ metadata: executionMetadata,
4233
4822
  req,
4234
4823
  res,
4235
4824
  agent: this
4236
4825
  });
4237
4826
  return ExecutionContext.run(execCtx, async () => {
4827
+ this.executionLogger.system("execution.started", "Execution started", {
4828
+ target: params.targetName,
4829
+ reasonerId: executionMetadata.reasonerId,
4830
+ executionId: executionMetadata.executionId,
4831
+ parentExecutionId: executionMetadata.parentExecutionId,
4832
+ runId: executionMetadata.runId,
4833
+ workflowId: executionMetadata.workflowId,
4834
+ rootWorkflowId: executionMetadata.rootWorkflowId
4835
+ });
4836
+ this.executionLogger.system("skill.started", "Skill execution started", {
4837
+ target: params.targetName,
4838
+ executionId: executionMetadata.executionId,
4839
+ runId: executionMetadata.runId,
4840
+ workflowId: executionMetadata.workflowId,
4841
+ rootWorkflowId: executionMetadata.rootWorkflowId
4842
+ });
4238
4843
  try {
4239
4844
  const ctx = new SkillContext({
4240
4845
  input: params.input,
4241
- executionId: params.metadata.executionId,
4242
- sessionId: params.metadata.sessionId,
4243
- workflowId: params.metadata.workflowId,
4846
+ executionId: executionMetadata.executionId,
4847
+ sessionId: executionMetadata.sessionId,
4848
+ workflowId: executionMetadata.workflowId,
4849
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4850
+ reasonerId: executionMetadata.reasonerId,
4244
4851
  req,
4245
4852
  res,
4246
4853
  agent: this,
4247
- memory: this.getMemoryInterface(params.metadata),
4248
- workflow: this.getWorkflowReporter(params.metadata),
4249
- did: this.getDidInterface(params.metadata, params.input, params.targetName)
4854
+ logger: this.executionLogger,
4855
+ memory: this.getMemoryInterface(executionMetadata),
4856
+ workflow: this.getWorkflowReporter(executionMetadata),
4857
+ did: this.getDidInterface(executionMetadata, params.input, params.targetName)
4250
4858
  });
4251
4859
  const result = await skill.handler(ctx);
4860
+ this.executionLogger.system("skill.completed", "Skill execution completed", {
4861
+ target: params.targetName,
4862
+ executionId: executionMetadata.executionId,
4863
+ runId: executionMetadata.runId,
4864
+ workflowId: executionMetadata.workflowId,
4865
+ rootWorkflowId: executionMetadata.rootWorkflowId
4866
+ });
4867
+ this.executionLogger.system("execution.completed", "Execution completed", {
4868
+ target: params.targetName,
4869
+ reasonerId: executionMetadata.reasonerId,
4870
+ executionId: executionMetadata.executionId,
4871
+ runId: executionMetadata.runId,
4872
+ workflowId: executionMetadata.workflowId,
4873
+ rootWorkflowId: executionMetadata.rootWorkflowId
4874
+ });
4252
4875
  if (params.respond && params.res) {
4253
4876
  params.res.json(result);
4254
4877
  return;
4255
4878
  }
4256
4879
  return result;
4257
4880
  } catch (err) {
4881
+ this.executionLogger.error("Skill execution failed", {
4882
+ target: params.targetName,
4883
+ executionId: executionMetadata.executionId,
4884
+ parentExecutionId: executionMetadata.parentExecutionId,
4885
+ runId: executionMetadata.runId,
4886
+ workflowId: executionMetadata.workflowId,
4887
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4888
+ error: err?.message ?? "Execution failed"
4889
+ }, {
4890
+ eventType: "skill.failed",
4891
+ source: "sdk.runtime",
4892
+ systemGenerated: true
4893
+ });
4894
+ this.executionLogger.error("Execution failed", {
4895
+ target: params.targetName,
4896
+ reasonerId: executionMetadata.reasonerId,
4897
+ executionId: executionMetadata.executionId,
4898
+ parentExecutionId: executionMetadata.parentExecutionId,
4899
+ runId: executionMetadata.runId,
4900
+ workflowId: executionMetadata.workflowId,
4901
+ rootWorkflowId: executionMetadata.rootWorkflowId,
4902
+ error: err?.message ?? "Execution failed"
4903
+ }, {
4904
+ eventType: "execution.failed",
4905
+ source: "sdk.runtime",
4906
+ systemGenerated: true
4907
+ });
4258
4908
  if (params.respond && params.res) {
4259
4909
  const body = { error: err?.message ?? "Execution failed" };
4260
4910
  if (err?.responseData) body.error_details = err.responseData;
@@ -4321,7 +4971,7 @@ var Agent = class {
4321
4971
  const timeoutMs = 5 * 60 * 1e3;
4322
4972
  const deadline = Date.now() + timeoutMs;
4323
4973
  while (Date.now() < deadline) {
4324
- await new Promise((resolve) => setTimeout(resolve, pollInterval));
4974
+ await new Promise((resolve2) => setTimeout(resolve2, pollInterval));
4325
4975
  try {
4326
4976
  const node = await this.agentFieldClient.getNode(this.config.nodeId);
4327
4977
  const status = node?.lifecycle_status;
@@ -4412,6 +5062,589 @@ var AgentRouter = class {
4412
5062
  function sanitize(value) {
4413
5063
  return value.replace(/[^0-9a-zA-Z]+/g, "_").replace(/_+/g, "_").replace(/^_+|_+$/g, "");
4414
5064
  }
5065
+ var IMAGE_MIME_TYPES = {
5066
+ ".jpg": "image/jpeg",
5067
+ ".jpeg": "image/jpeg",
5068
+ ".png": "image/png",
5069
+ ".gif": "image/gif",
5070
+ ".webp": "image/webp",
5071
+ ".bmp": "image/bmp"
5072
+ };
5073
+ var AUDIO_MIME_TYPES = {
5074
+ ".wav": "audio/wav",
5075
+ ".mp3": "audio/mpeg",
5076
+ ".flac": "audio/flac",
5077
+ ".ogg": "audio/ogg"
5078
+ };
5079
+ var Text = class {
5080
+ type = "text";
5081
+ text;
5082
+ constructor(text2) {
5083
+ this.text = text2;
5084
+ }
5085
+ };
5086
+ var Image = class _Image {
5087
+ type = "image_url";
5088
+ imageUrl;
5089
+ constructor(imageUrl) {
5090
+ this.imageUrl = imageUrl;
5091
+ }
5092
+ /**
5093
+ * Create Image from a local file by converting to base64 data URL.
5094
+ */
5095
+ static async fromFile(filePath, detail = "high") {
5096
+ const absolutePath = resolve(filePath);
5097
+ const buffer = await readFile(absolutePath);
5098
+ const base64Data = buffer.toString("base64");
5099
+ const ext = getExtension(absolutePath).toLowerCase();
5100
+ const mimeType = IMAGE_MIME_TYPES[ext] || "image/jpeg";
5101
+ const dataUrl = `data:${mimeType};base64,${base64Data}`;
5102
+ return new _Image({ url: dataUrl, detail });
5103
+ }
5104
+ /**
5105
+ * Create Image from a URL.
5106
+ */
5107
+ static fromUrl(url, detail = "high") {
5108
+ return new _Image({ url, detail });
5109
+ }
5110
+ /**
5111
+ * Create Image from a buffer.
5112
+ */
5113
+ static async fromBuffer(buffer, mimeType = "image/jpeg", detail = "high") {
5114
+ const base64Data = Buffer.from(buffer).toString("base64");
5115
+ const dataUrl = `data:${mimeType};base64,${base64Data}`;
5116
+ return new _Image({ url: dataUrl, detail });
5117
+ }
5118
+ /**
5119
+ * Create Image from a base64 string.
5120
+ */
5121
+ static async fromBase64(base64Data, mimeType = "image/jpeg", detail = "high") {
5122
+ const dataUrl = `data:${mimeType};base64,${base64Data}`;
5123
+ return new _Image({ url: dataUrl, detail });
5124
+ }
5125
+ };
5126
+ var Audio = class _Audio {
5127
+ type = "input_audio";
5128
+ audio;
5129
+ constructor(audio) {
5130
+ this.audio = audio;
5131
+ }
5132
+ /**
5133
+ * Create Audio from a local file by converting to base64.
5134
+ */
5135
+ static async fromFile(filePath, format) {
5136
+ const absolutePath = resolve(filePath);
5137
+ const ext = getExtension(absolutePath).toLowerCase().replace(".", "");
5138
+ const audioFormat = format || (["wav", "mp3", "flac", "ogg"].includes(ext) ? ext : "wav");
5139
+ const buffer = await readFile(absolutePath);
5140
+ const base64Data = buffer.toString("base64");
5141
+ return new _Audio({ data: base64Data, format: audioFormat });
5142
+ }
5143
+ /**
5144
+ * Create Audio from a URL (downloads and converts to base64).
5145
+ */
5146
+ static async fromUrl(url, format = "wav") {
5147
+ try {
5148
+ const response = await fetch(url);
5149
+ if (!response.ok) {
5150
+ throw new Error(`Failed to fetch audio from URL: ${response.status} ${response.statusText}`);
5151
+ }
5152
+ const arrayBuffer = await response.arrayBuffer();
5153
+ const base64Data = Buffer.from(arrayBuffer).toString("base64");
5154
+ return new _Audio({ data: base64Data, format });
5155
+ } catch (error) {
5156
+ if (error instanceof TypeError && error.message.includes("fetch")) {
5157
+ throw new Error("URL download requires a fetch-compatible environment");
5158
+ }
5159
+ throw error;
5160
+ }
5161
+ }
5162
+ /**
5163
+ * Create Audio from a buffer.
5164
+ */
5165
+ static async fromBuffer(buffer, format = "wav") {
5166
+ const base64Data = Buffer.from(buffer).toString("base64");
5167
+ return new _Audio({ data: base64Data, format });
5168
+ }
5169
+ /**
5170
+ * Create Audio from a base64 string.
5171
+ */
5172
+ static async fromBase64(base64Data, format = "wav") {
5173
+ return new _Audio({ data: base64Data, format });
5174
+ }
5175
+ };
5176
+ var File = class _File {
5177
+ type = "file";
5178
+ file;
5179
+ constructor(file) {
5180
+ this.file = file;
5181
+ }
5182
+ /**
5183
+ * Create File from a local file path.
5184
+ */
5185
+ static async fromFile(filePath, mimeType) {
5186
+ const absolutePath = resolve(filePath);
5187
+ const detectedMimeType = mimeType || guessMimeType(absolutePath) || "application/octet-stream";
5188
+ const buffer = await readFile(absolutePath);
5189
+ const base64Data = buffer.toString("base64");
5190
+ const dataUrl = `data:${detectedMimeType};base64,${base64Data}`;
5191
+ return new _File({ url: dataUrl, mimeType: detectedMimeType });
5192
+ }
5193
+ /**
5194
+ * Create File from a URL.
5195
+ */
5196
+ static fromUrl(url, mimeType) {
5197
+ return new _File({ url, mimeType });
5198
+ }
5199
+ /**
5200
+ * Create File from a buffer.
5201
+ */
5202
+ static async fromBuffer(buffer, mimeType) {
5203
+ const base64Data = Buffer.from(buffer).toString("base64");
5204
+ const dataUrl = `data:${mimeType};base64,${base64Data}`;
5205
+ return new _File({ url: dataUrl, mimeType });
5206
+ }
5207
+ /**
5208
+ * Create File from a base64 string.
5209
+ */
5210
+ static async fromBase64(base64Data, mimeType) {
5211
+ const dataUrl = `data:${mimeType};base64,${base64Data}`;
5212
+ return new _File({ url: dataUrl, mimeType });
5213
+ }
5214
+ };
5215
+ function getExtension(filePath) {
5216
+ const lastDot = filePath.lastIndexOf(".");
5217
+ if (lastDot === -1) {
5218
+ return "";
5219
+ }
5220
+ return filePath.slice(lastDot);
5221
+ }
5222
+ function guessMimeType(filePath) {
5223
+ const ext = getExtension(filePath).toLowerCase();
5224
+ if (ext in IMAGE_MIME_TYPES) {
5225
+ return IMAGE_MIME_TYPES[ext];
5226
+ }
5227
+ if (ext in AUDIO_MIME_TYPES) {
5228
+ return AUDIO_MIME_TYPES[ext];
5229
+ }
5230
+ const documentMimeTypes = {
5231
+ ".pdf": "application/pdf",
5232
+ ".doc": "application/msword",
5233
+ ".docx": "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
5234
+ ".xls": "application/vnd.ms-excel",
5235
+ ".xlsx": "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
5236
+ ".txt": "text/plain",
5237
+ ".csv": "text/csv",
5238
+ ".html": "text/html",
5239
+ ".json": "application/json",
5240
+ ".xml": "application/xml",
5241
+ ".zip": "application/zip"
5242
+ };
5243
+ return documentMimeTypes[ext] || null;
5244
+ }
5245
+ function text(content) {
5246
+ return new Text(content);
5247
+ }
5248
+ async function imageFromFile(filePath, detail = "high") {
5249
+ return Image.fromFile(filePath, detail);
5250
+ }
5251
+ function imageFromUrl(url, detail = "high") {
5252
+ return Image.fromUrl(url, detail);
5253
+ }
5254
+ async function imageFromBuffer(buffer, mimeType = "image/jpeg", detail = "high") {
5255
+ return Image.fromBuffer(buffer, mimeType, detail);
5256
+ }
5257
+ async function imageFromBase64(base64Data, mimeType, detail = "high") {
5258
+ return Image.fromBase64(base64Data, mimeType, detail);
5259
+ }
5260
+ async function audioFromFile(filePath, format) {
5261
+ return Audio.fromFile(filePath, format);
5262
+ }
5263
+ async function audioFromUrl(url, format = "wav") {
5264
+ return Audio.fromUrl(url, format);
5265
+ }
5266
+ async function audioFromBuffer(buffer, format = "wav") {
5267
+ return Audio.fromBuffer(buffer, format);
5268
+ }
5269
+ async function audioFromBase64(base64Data, format = "wav") {
5270
+ return Audio.fromBase64(base64Data, format);
5271
+ }
5272
+ async function fileFromPath(filePath, mimeType) {
5273
+ return File.fromFile(filePath, mimeType);
5274
+ }
5275
+ function fileFromUrl(url, mimeType) {
5276
+ return File.fromUrl(url, mimeType);
5277
+ }
5278
+ async function fileFromBuffer(buffer, mimeType) {
5279
+ return File.fromBuffer(buffer, mimeType);
5280
+ }
5281
+ async function fileFromBase64(base64Data, mimeType) {
5282
+ return File.fromBase64(base64Data, mimeType);
5283
+ }
5284
+ var MultimodalResponse = class {
5285
+ _text;
5286
+ _audio;
5287
+ _images;
5288
+ _files;
5289
+ _rawResponse;
5290
+ _costUsd;
5291
+ _usage;
5292
+ constructor(text2 = "", audio = null, images = [], files = [], rawResponse = null, costUsd = null, usage = {}) {
5293
+ this._text = text2;
5294
+ this._audio = audio;
5295
+ this._images = images;
5296
+ this._files = files;
5297
+ this._rawResponse = rawResponse;
5298
+ this._costUsd = costUsd;
5299
+ this._usage = usage;
5300
+ }
5301
+ /**
5302
+ * Get text content.
5303
+ */
5304
+ get text() {
5305
+ return this._text;
5306
+ }
5307
+ /**
5308
+ * Get audio output if available.
5309
+ */
5310
+ get audio() {
5311
+ return this._audio;
5312
+ }
5313
+ /**
5314
+ * Get list of image outputs.
5315
+ */
5316
+ get images() {
5317
+ return this._images;
5318
+ }
5319
+ /**
5320
+ * Get list of file outputs.
5321
+ */
5322
+ get files() {
5323
+ return this._files;
5324
+ }
5325
+ /**
5326
+ * Check if response contains audio.
5327
+ */
5328
+ hasAudio() {
5329
+ return this._audio !== null;
5330
+ }
5331
+ /**
5332
+ * Check if response contains images.
5333
+ */
5334
+ hasImage() {
5335
+ return this._images.length > 0;
5336
+ }
5337
+ /**
5338
+ * Check if response contains files.
5339
+ */
5340
+ hasFile() {
5341
+ return this._files.length > 0;
5342
+ }
5343
+ /**
5344
+ * Check if response contains any multimodal content.
5345
+ */
5346
+ isMultimodal() {
5347
+ return this.hasAudio() || this.hasImage() || this.hasFile();
5348
+ }
5349
+ /**
5350
+ * Get the raw LLM response object.
5351
+ */
5352
+ get rawResponse() {
5353
+ return this._rawResponse;
5354
+ }
5355
+ /**
5356
+ * Estimated cost of this LLM call in USD, if available.
5357
+ */
5358
+ get costUsd() {
5359
+ return this._costUsd;
5360
+ }
5361
+ /**
5362
+ * Token usage breakdown.
5363
+ */
5364
+ get usage() {
5365
+ return this._usage;
5366
+ }
5367
+ /**
5368
+ * Get all images.
5369
+ * Alias for images property for API consistency.
5370
+ */
5371
+ getImages() {
5372
+ return this._images;
5373
+ }
5374
+ /**
5375
+ * Get audio.
5376
+ * Alias for audio property for API consistency.
5377
+ */
5378
+ getAudio() {
5379
+ return this._audio;
5380
+ }
5381
+ /**
5382
+ * Get all files.
5383
+ * Alias for files property for API consistency.
5384
+ */
5385
+ getFiles() {
5386
+ return this._files;
5387
+ }
5388
+ /**
5389
+ * Get raw image bytes from an ImageOutput.
5390
+ */
5391
+ decodeBase64(data) {
5392
+ return new Uint8Array(Buffer.from(data, "base64"));
5393
+ }
5394
+ async getUrlBytes(sourceUrl) {
5395
+ if (sourceUrl.startsWith("data:")) {
5396
+ const base64Data = sourceUrl.split(",", 2)[1];
5397
+ if (!base64Data) {
5398
+ throw new Error("Invalid data URL");
5399
+ }
5400
+ return this.decodeBase64(base64Data);
5401
+ }
5402
+ const response = await fetch(sourceUrl);
5403
+ if (!response.ok) {
5404
+ throw new Error(`Failed to download multimodal asset: ${response.status} ${response.statusText}`);
5405
+ }
5406
+ const arrayBuffer = await response.arrayBuffer();
5407
+ return new Uint8Array(arrayBuffer);
5408
+ }
5409
+ async getImageBytes(image) {
5410
+ if (image.b64Json) {
5411
+ return this.decodeBase64(image.b64Json);
5412
+ } else if (image.url) {
5413
+ return this.getUrlBytes(image.url);
5414
+ }
5415
+ throw new Error("No image data available");
5416
+ }
5417
+ /**
5418
+ * Get raw audio bytes from an AudioOutput.
5419
+ */
5420
+ async getAudioBytes(audio) {
5421
+ if (audio.data) {
5422
+ return this.decodeBase64(audio.data);
5423
+ }
5424
+ if (audio.url) {
5425
+ return this.getUrlBytes(audio.url);
5426
+ }
5427
+ throw new Error("No audio data available");
5428
+ }
5429
+ /**
5430
+ * Get raw file bytes from a FileOutput.
5431
+ */
5432
+ async getFileBytes(file) {
5433
+ if (file.data) {
5434
+ return this.decodeBase64(file.data);
5435
+ }
5436
+ if (file.url) {
5437
+ return this.getUrlBytes(file.url);
5438
+ }
5439
+ throw new Error("No file data available");
5440
+ }
5441
+ /**
5442
+ * Save a single image to file.
5443
+ */
5444
+ async saveImage(image, imagePath) {
5445
+ const bytes = await this.getImageBytes(image);
5446
+ await promises.mkdir(path2.dirname(imagePath), { recursive: true });
5447
+ await promises.writeFile(imagePath, bytes);
5448
+ }
5449
+ /**
5450
+ * Save a single audio to file.
5451
+ */
5452
+ async saveAudio(audio, audioPath) {
5453
+ const bytes = await this.getAudioBytes(audio);
5454
+ await promises.mkdir(path2.dirname(audioPath), { recursive: true });
5455
+ await promises.writeFile(audioPath, bytes);
5456
+ }
5457
+ /**
5458
+ * Save a single file to disk.
5459
+ */
5460
+ async saveFile(file, filePath) {
5461
+ const bytes = await this.getFileBytes(file);
5462
+ await promises.mkdir(path2.dirname(filePath), { recursive: true });
5463
+ await promises.writeFile(filePath, bytes);
5464
+ }
5465
+ /**
5466
+ * Save all multimodal content to a directory.
5467
+ * Returns a dict mapping content type to saved file paths.
5468
+ */
5469
+ async save(outputDir, prefix = "output") {
5470
+ const savedFiles = {};
5471
+ await promises.mkdir(outputDir, { recursive: true });
5472
+ if (this._audio) {
5473
+ const audioPath = path2.join(outputDir, `${prefix}_audio.${this._audio.format}`);
5474
+ await this.saveAudio(this._audio, audioPath);
5475
+ savedFiles["audio"] = audioPath;
5476
+ }
5477
+ for (let i = 0; i < this._images.length; i++) {
5478
+ const image = this._images[i];
5479
+ let ext = "png";
5480
+ if (image.url) {
5481
+ const urlExt = path2.extname(image.url).slice(1);
5482
+ if (urlExt) ext = urlExt;
5483
+ }
5484
+ const imagePath = path2.join(outputDir, `${prefix}_image_${i}.${ext}`);
5485
+ await this.saveImage(image, imagePath);
5486
+ savedFiles[`image_${i}`] = imagePath;
5487
+ }
5488
+ for (let i = 0; i < this._files.length; i++) {
5489
+ const file = this._files[i];
5490
+ const filename = file.filename || `${prefix}_file_${i}`;
5491
+ const filePath = path2.join(outputDir, filename);
5492
+ await this.saveFile(file, filePath);
5493
+ savedFiles[`file_${i}`] = filePath;
5494
+ }
5495
+ if (this._text) {
5496
+ const textPath = path2.join(outputDir, `${prefix}_text.txt`);
5497
+ await promises.writeFile(textPath, this._text, "utf-8");
5498
+ savedFiles["text"] = textPath;
5499
+ }
5500
+ return savedFiles;
5501
+ }
5502
+ /**
5503
+ * String representation for backward compatibility.
5504
+ */
5505
+ toString() {
5506
+ return this._text;
5507
+ }
5508
+ /**
5509
+ * Developer-friendly representation.
5510
+ */
5511
+ toJSON() {
5512
+ const parts = [];
5513
+ if (this._audio) parts.push(`audio=${this._audio.format}`);
5514
+ if (this._images.length > 0) parts.push(`images=${this._images.length}`);
5515
+ if (this._files.length > 0) parts.push(`files=${this._files.length}`);
5516
+ return {
5517
+ text: this._text,
5518
+ audio: this._audio,
5519
+ images: this._images,
5520
+ files: this._files,
5521
+ _debug: `MultimodalResponse(${parts.join(", ")})`
5522
+ };
5523
+ }
5524
+ };
5525
+ function createMultimodalResponse(rawResponse, text2 = "") {
5526
+ let audio = null;
5527
+ let images = [];
5528
+ let files = [];
5529
+ const extractedImages = extractImages(rawResponse);
5530
+ if (extractedImages.length > 0) {
5531
+ images = extractedImages;
5532
+ }
5533
+ const extractedAudio = extractAudio(rawResponse);
5534
+ if (extractedAudio) {
5535
+ audio = extractedAudio;
5536
+ }
5537
+ const extractedFiles = extractFiles(rawResponse);
5538
+ if (extractedFiles.length > 0) {
5539
+ files = extractedFiles;
5540
+ }
5541
+ return new MultimodalResponse(text2, audio, images, files, rawResponse);
5542
+ }
5543
+ function extractImages(data) {
5544
+ const images = [];
5545
+ if (!data) return images;
5546
+ if (Array.isArray(data)) {
5547
+ for (const item of data) {
5548
+ const extracted = extractSingleImage(item);
5549
+ if (extracted) images.push(extracted);
5550
+ }
5551
+ return images;
5552
+ }
5553
+ if (typeof data === "object") {
5554
+ const obj = data;
5555
+ if (Array.isArray(obj.images)) {
5556
+ for (const img of obj.images) {
5557
+ const extracted = extractSingleImage(img);
5558
+ if (extracted) images.push(extracted);
5559
+ }
5560
+ }
5561
+ if (obj.image_url) {
5562
+ const extracted = extractSingleImage(obj.image_url);
5563
+ if (extracted) images.push(extracted);
5564
+ }
5565
+ if (obj.url || obj.b64_json || obj.b64Json) {
5566
+ const extracted = extractSingleImage(obj);
5567
+ if (extracted) images.push(extracted);
5568
+ }
5569
+ }
5570
+ return images;
5571
+ }
5572
+ function extractSingleImage(data) {
5573
+ if (!data) return null;
5574
+ if (typeof data === "string") {
5575
+ if (data.startsWith("http") || data.startsWith("data:")) {
5576
+ return { url: data };
5577
+ }
5578
+ return null;
5579
+ }
5580
+ if (typeof data === "object") {
5581
+ const obj = data;
5582
+ if (obj.image_url) {
5583
+ const imageUrl = obj.image_url;
5584
+ const url2 = imageUrl.url;
5585
+ if (url2) {
5586
+ if (url2.startsWith("data:image")) {
5587
+ const base64Data = url2.split(",", 2)[1];
5588
+ return { url: url2, b64Json: base64Data || void 0 };
5589
+ }
5590
+ return { url: url2 };
5591
+ }
5592
+ }
5593
+ const url = obj.url || obj.image_url;
5594
+ const b64Json = obj.b64_json || obj.b64Json;
5595
+ const revisedPrompt = obj.revised_prompt || obj.revisedPrompt;
5596
+ if (url || b64Json) {
5597
+ return { url, b64Json, revisedPrompt };
5598
+ }
5599
+ }
5600
+ return null;
5601
+ }
5602
+ function extractAudio(data) {
5603
+ if (!data || typeof data !== "object") return null;
5604
+ const obj = data;
5605
+ if (obj.audio && typeof obj.audio === "object") {
5606
+ const audio = obj.audio;
5607
+ return {
5608
+ data: audio.data,
5609
+ format: audio.format || "wav",
5610
+ url: audio.url
5611
+ };
5612
+ }
5613
+ if (obj.input_audio && typeof obj.input_audio === "object") {
5614
+ const inputAudio = obj.input_audio;
5615
+ return {
5616
+ data: inputAudio.data,
5617
+ format: inputAudio.format || "wav"
5618
+ };
5619
+ }
5620
+ return null;
5621
+ }
5622
+ function extractFiles(data) {
5623
+ const files = [];
5624
+ if (!data) return files;
5625
+ if (typeof data === "object") {
5626
+ const obj = data;
5627
+ if (Array.isArray(obj.files)) {
5628
+ for (const file of obj.files) {
5629
+ const extracted = extractSingleFile(file);
5630
+ if (extracted) files.push(extracted);
5631
+ }
5632
+ }
5633
+ }
5634
+ return files;
5635
+ }
5636
+ function extractSingleFile(data) {
5637
+ if (!data || typeof data !== "object") return null;
5638
+ const obj = data;
5639
+ const url = obj.url;
5640
+ const data_b64 = obj.data;
5641
+ const mimeType = obj.mime_type || obj.mimeType;
5642
+ const filename = obj.filename;
5643
+ if (url || data_b64) {
5644
+ return { url, data: data_b64, mimeType, filename };
5645
+ }
5646
+ return null;
5647
+ }
4415
5648
 
4416
5649
  // src/harness/index.ts
4417
5650
  init_types();
@@ -4574,9 +5807,9 @@ var ApprovalClient = class {
4574
5807
  }
4575
5808
  };
4576
5809
  function sleep(ms) {
4577
- return new Promise((resolve) => setTimeout(resolve, ms));
5810
+ return new Promise((resolve2) => setTimeout(resolve2, ms));
4578
5811
  }
4579
5812
 
4580
- export { ACTIVE_STATUSES, AIClient, Agent, AgentRouter, ApprovalClient, CANONICAL_STATUSES, DIDAuthenticator, DidClient, DidInterface, DidManager, ExecutionContext, ExecutionStatus, HEADER_CALLER_DID, HEADER_DID_NONCE, HEADER_DID_SIGNATURE, HEADER_DID_TIMESTAMP, HarnessRunner, MCPClient, MCPClientRegistry, MCPToolRegistrar, MemoryClient, MemoryClientBase, MemoryEventClient, MemoryInterface, RateLimitError, ReasonerContext, SUPPORTED_PROVIDERS, SkillContext, StatelessRateLimiter, TERMINAL_STATUSES, WorkflowReporter, buildProvider, buildToolConfig, capabilitiesToTools, capabilityToMetadataTool, capabilityToTool, createHarnessResult, createMetrics, createRawResult, executeToolCallLoop, getCurrentContext, getCurrentSkillContext, isActive, isTerminal, normalizeStatus };
5813
+ export { ACTIVE_STATUSES, AIClient, Agent, AgentRouter, ApprovalClient, Audio, CANONICAL_STATUSES, DIDAuthenticator, DidClient, DidInterface, DidManager, ExecutionContext, ExecutionLogger, ExecutionStatus, File, HEADER_CALLER_DID, HEADER_DID_NONCE, HEADER_DID_SIGNATURE, HEADER_DID_TIMESTAMP, HarnessRunner, Image, MCPClient, MCPClientRegistry, MCPToolRegistrar, MemoryClient, MemoryClientBase, MemoryEventClient, MemoryInterface, MultimodalResponse, RateLimitError, ReasonerContext, SUPPORTED_PROVIDERS, SkillContext, StatelessRateLimiter, TERMINAL_STATUSES, Text, WorkflowReporter, audioFromBase64, audioFromBuffer, audioFromFile, audioFromUrl, buildProvider, buildToolConfig, capabilitiesToTools, capabilityToMetadataTool, capabilityToTool, createExecutionLogger, createHarnessResult, createMetrics, createMultimodalResponse, createRawResult, executeToolCallLoop, fileFromBase64, fileFromBuffer, fileFromPath, fileFromUrl, getCurrentContext, getCurrentSkillContext, imageFromBase64, imageFromBuffer, imageFromFile, imageFromUrl, isActive, isExecutionLogBatchPayload, isTerminal, normalizeExecutionLogEntry, normalizeStatus, serializeExecutionLogEntry, text };
4581
5814
  //# sourceMappingURL=index.js.map
4582
5815
  //# sourceMappingURL=index.js.map