@cap-js/agents 0.9.4 → 0.9.5

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.
@@ -9,7 +9,14 @@ import { convertUsageData } from "../../lib/telemetry/chat-tracing.js"
9
9
  import { triggerCleanup } from "../../lib/protocol/persistence/cleanup.js"
10
10
  import { COLLECT_RESULT } from "./chat.js"
11
11
  import { linkTraceToPrompt } from "../../lib/telemetry/mlflow/tracing.js"
12
- import { handleHitlInterrupt, requiresHitl, resumeHitl } from "./graph-executor/hitl.js"
12
+ import {
13
+ handleHitlInterrupt,
14
+ isTimeoutHitl,
15
+ publishTimeoutHitl,
16
+ requiresHitl,
17
+ resumeHitl,
18
+ resumeTimeoutHitl,
19
+ } from "./graph-executor/hitl.js"
13
20
 
14
21
  const LOG = cds.log("agents")
15
22
 
@@ -145,7 +152,7 @@ class GraphExecutor {
145
152
  abort(taskId) {
146
153
  const controller = this._abortControllers.get(taskId)
147
154
  if (controller && !controller.signal.aborted) {
148
- LOG.info("aborting", { task: short(taskId), service: this._srv.name })
155
+ LOG.info(this._srv.name, "aborting", { task: short(taskId) })
149
156
  controller.abort()
150
157
  }
151
158
  }
@@ -163,7 +170,7 @@ class GraphExecutor {
163
170
  const { CdsCheckpointSaver } =
164
171
  await import("../../lib/protocol/persistence/checkpoint-saver.js")
165
172
  resolved.checkpointer = new CdsCheckpointSaver()
166
- LOG.debug("Auto-injected CdsCheckpointSaver", { service: this._srv.name })
173
+ LOG.debug(this._srv.name, "- auto-injected CdsCheckpointSaver")
167
174
  }
168
175
  this._graph = resolved
169
176
  return this._graph
@@ -174,12 +181,10 @@ class GraphExecutor {
174
181
  * per-token artifact-update SSE events as LLM tokens arrive.
175
182
  */
176
183
  async _streamWithPublish(graph, input, config, eventBus, taskId, contextId, signal) {
177
- const maxExecution = ms4(cds.env.agents?.pool?.maxExecutionTimePerTask || "5min")
178
- const grace = this._getGrace()
179
- const softTimeout = Math.max(maxExecution - grace, 1000)
184
+ const maxExecution = ms4(cds.env.agents?.quotas?.maxExecutionTimePerTask || "5min")
180
185
 
181
186
  const controller = new AbortController()
182
- const timeoutHandle = setTimeout(() => controller.abort(), softTimeout)
187
+ const timeoutHandle = setTimeout(() => controller.abort(), maxExecution)
183
188
  const combinedSignal = signal ? AbortSignal.any([signal, controller.signal]) : controller.signal
184
189
 
185
190
  let tokenCount = 0
@@ -271,8 +276,8 @@ class GraphExecutor {
271
276
  if (signal?.aborted) {
272
277
  throw new AbortError("Task execution aborted")
273
278
  }
274
- throw new TimeoutError(`Graph execution timed out after ${softTimeout / 1000}s`, {
275
- timeout: softTimeout,
279
+ throw new TimeoutError(`Graph execution timed out after ${maxExecution / 1000}s`, {
280
+ timeout: maxExecution,
276
281
  })
277
282
  }
278
283
  throw err
@@ -312,23 +317,13 @@ class GraphExecutor {
312
317
 
313
318
  return { state: finalState, tokenCount }
314
319
  }
315
- /**
316
- * Parse configured timeout grace period.
317
- */
318
- _getGrace() {
319
- return ms4(cds.env.agents?.pool?.timeoutGrace ?? "15s")
320
- }
321
-
322
320
  async _invokeWithTimeout(graph, input, config, signal) {
323
- const maxExecution = ms4(cds.env.agents?.pool?.maxExecutionTimePerTask || "5min")
324
- const grace = this._getGrace()
325
- // Soft timeout fires early to allow graceful summarization
326
- const softTimeout = Math.max(maxExecution - grace, 1000)
321
+ const maxExecution = ms4(cds.env.agents?.quotas?.maxExecutionTimePerTask || "5min")
327
322
 
328
323
  // Use explicit AbortController + setTimeout (reffed timer keeps event loop alive)
329
324
  // instead of AbortSignal.timeout() which uses an unreffed timer
330
325
  const timeoutController = new AbortController()
331
- const timer = setTimeout(() => timeoutController.abort(), softTimeout)
326
+ const timer = setTimeout(() => timeoutController.abort(), maxExecution)
332
327
 
333
328
  // Combine caller-provided abort signal with timeout
334
329
  const combinedSignal = signal
@@ -344,8 +339,8 @@ class GraphExecutor {
344
339
  if (signal?.aborted) {
345
340
  throw new AbortError("Task execution aborted")
346
341
  }
347
- throw new TimeoutError(`Graph execution timed out after ${softTimeout / 1000}s`, {
348
- timeout: softTimeout,
342
+ throw new TimeoutError(`Graph execution timed out after ${maxExecution / 1000}s`, {
343
+ timeout: maxExecution,
349
344
  })
350
345
  }
351
346
  throw err
@@ -359,7 +354,6 @@ class GraphExecutor {
359
354
  */
360
355
  async _summarizePartialWork(taskId, contextId, serviceName, reason) {
361
356
  const { summarizePartialWork } = await import("../../lib/agents/summarize-on-timeout.js")
362
- const grace = this._getGrace()
363
357
  return summarizePartialWork({
364
358
  taskId,
365
359
  contextId,
@@ -367,7 +361,8 @@ class GraphExecutor {
367
361
  reason,
368
362
  checkpointer: this._graph?.checkpointer,
369
363
  getModel: () => this._srv.send("buildModel"),
370
- timeout: Math.max(grace - 2000, grace * 0.8, 500),
364
+ // Summary runs after graph abort, so no execution-time grace is needed.
365
+ timeout: 10_000,
371
366
  })
372
367
  }
373
368
 
@@ -447,9 +442,8 @@ class GraphExecutor {
447
442
  cds.env.agents?.fileIO,
448
443
  )
449
444
  if (rejection) {
450
- LOG.warn("input file rejected", {
445
+ LOG.warn(serviceName, "-", "input file rejected", {
451
446
  conversation: short(contextId),
452
- service: serviceName,
453
447
  name: safeName,
454
448
  mimeType: safeMime,
455
449
  reason: rejection,
@@ -458,9 +452,8 @@ class GraphExecutor {
458
452
  }
459
453
  const buf = Buffer.from(file.bytes, "base64")
460
454
  await fileStore.saveInputFile(taskId, safeName, safeMime, buf)
461
- LOG.info("file uploaded", {
455
+ LOG.info(serviceName, "-", "file uploaded", {
462
456
  conversation: short(contextId),
463
- service: serviceName,
464
457
  name: safeName,
465
458
  mimeType: safeMime,
466
459
  size: buf.length,
@@ -564,7 +557,8 @@ class GraphExecutor {
564
557
  const t0 = Date.now()
565
558
 
566
559
  if (isResume) {
567
- result = await resumeHitl({
560
+ const resume = isTimeoutHitl(requestContext.task) ? resumeTimeoutHitl : resumeHitl
561
+ result = await resume({
568
562
  requestContext,
569
563
  graph,
570
564
  config,
@@ -619,7 +613,7 @@ class GraphExecutor {
619
613
  const outputMapper = this._outputMapper || defaultOutputMapper
620
614
  const output = outputMapper(result) || "I could not generate a response."
621
615
 
622
- LOG.info("completed", { conversation: short(contextId), service: serviceName, duration })
616
+ LOG.info(serviceName, "completed", { conversation: short(contextId), duration })
623
617
 
624
618
  if (wfSpan) {
625
619
  wfSpan.setAttribute("agent.outcome", "completed")
@@ -750,9 +744,8 @@ class GraphExecutor {
750
744
  ? Buffer.byteLength(artifact.file.bytes, "base64")
751
745
  : 0
752
746
  if (declaredBytes > maxFileBytes) {
753
- LOG.warn("emit_file_part artifact exceeds cap; skipping", {
747
+ LOG.warn(serviceName, "-", "emit_file_part artifact exceeds cap; skipping", {
754
748
  conversation: short(contextId),
755
- service: serviceName,
756
749
  name: artifact.file?.name,
757
750
  size: declaredBytes,
758
751
  cap: maxFileBytes,
@@ -777,9 +770,8 @@ class GraphExecutor {
777
770
  const outputMeta = await fileStore.listOutputFilesMeta(taskId)
778
771
  for (const meta of outputMeta) {
779
772
  if (meta.size > maxFileBytes) {
780
- LOG.warn("output file exceeds cap; skipping", {
773
+ LOG.warn(serviceName, "-", "output file exceeds cap; skipping", {
781
774
  conversation: short(contextId),
782
- service: serviceName,
783
775
  name: meta.name,
784
776
  size: meta.size,
785
777
  cap: maxFileBytes,
@@ -798,7 +790,7 @@ class GraphExecutor {
798
790
  // Exclude emit_file_part outputs — those are this agent's own artifacts, not
799
791
  // downstream files, and re-persisting them would create spurious /uploads/ entries.
800
792
  // Enforce the same size + MIME guard as inbound uploads so a malicious
801
- // sub-agent cannot bypass the cap by echoing an oversized FilePart.
793
+ // subagent cannot bypass the cap by echoing an oversized FilePart.
802
794
  await Promise.all(
803
795
  fileArtifacts
804
796
  .slice(0, source1Count)
@@ -806,9 +798,8 @@ class GraphExecutor {
806
798
  if (!fa.file?.bytes || !fa.file?.name || fa._fromEmitFilePart) return false
807
799
  const rejection = checkInputFile(fa.file, cds.env.agents?.fileIO)
808
800
  if (rejection) {
809
- LOG.warn("downstream file re-persist rejected", {
801
+ LOG.warn(serviceName, "-", "downstream file re-persist rejected", {
810
802
  conversation: short(contextId),
811
- service: serviceName,
812
803
  name: fa.file.name,
813
804
  reason: rejection,
814
805
  })
@@ -828,9 +819,8 @@ class GraphExecutor {
828
819
  // Capture source classification for the log line below.
829
820
  for (const filePart of fileArtifacts) {
830
821
  if (!filePart.file?.name) {
831
- LOG.warn("skipping malformed file artifact", {
822
+ LOG.warn(serviceName, "-", "skipping malformed file artifact", {
832
823
  conversation: short(contextId),
833
- service: serviceName,
834
824
  })
835
825
  continue
836
826
  }
@@ -841,9 +831,8 @@ class GraphExecutor {
841
831
  typeof filePart.file?.bytes === "string"
842
832
  ? Buffer.byteLength(filePart.file.bytes, "base64")
843
833
  : 0
844
- LOG.info("file emitted", {
834
+ LOG.info(serviceName, "-", "file emitted", {
845
835
  conversation: short(contextId),
846
- service: serviceName,
847
836
  name: safeName,
848
837
  mimeType: filePart.file?.mimeType,
849
838
  bytes: decodedSize,
@@ -863,13 +852,12 @@ class GraphExecutor {
863
852
 
864
853
  dataArtifacts.forEach((artifact, i) => {
865
854
  if (artifact.data == null || typeof artifact.data !== "object") {
866
- LOG.warn("skipping malformed data artifact", {
855
+ LOG.warn(serviceName, "-", "skipping malformed data artifact", {
867
856
  conversation: short(contextId),
868
- service: serviceName,
869
857
  })
870
858
  return
871
859
  }
872
- LOG.info("data emitted", { conversation: short(contextId), service: serviceName })
860
+ LOG.info(serviceName, "-", "data emitted", { conversation: short(contextId) })
873
861
  eventBus.publish({
874
862
  kind: "artifact-update",
875
863
  taskId,
@@ -902,7 +890,7 @@ class GraphExecutor {
902
890
  // Aborted (client disconnect or tasks/cancel) — publish canceled, not failed
903
891
  // Use name check (not instanceof) to also catch native DOMException AbortError from LangGraph
904
892
  if (err.name === "AbortError") {
905
- LOG.info("canceled", { conversation: short(contextId), service: serviceName })
893
+ LOG.info(serviceName, "-", "canceled", { conversation: short(contextId) })
906
894
  if (wfSpan) wfSpan.setAttribute("agent.outcome", "canceled")
907
895
 
908
896
  audit("AgentTaskCanceled", {
@@ -923,62 +911,34 @@ class GraphExecutor {
923
911
  return
924
912
  }
925
913
 
926
- // Timeout — attempt graceful summary of work-in-progress before reporting
914
+ // Timeout — pause at checkpoint. User decides whether to resume graph.
927
915
  if (err.name === "TimeoutError") {
928
- LOG.warn("timeout", { conversation: short(contextId), service: serviceName })
916
+ LOG.warn(serviceName, "-", "timeout", { conversation: short(contextId) })
929
917
 
930
- if (wfSpan) wfSpan.setAttribute("agent.outcome", "timeout")
931
- metrics.errorsTotal.add(1, { ...mAttrs, "agent.error.code": "timeout" })
918
+ if (wfSpan) wfSpan.setAttribute("agent.outcome", "input-required")
932
919
 
933
920
  const summary = await this._summarizePartialWork(
934
921
  taskId,
935
922
  contextId,
936
923
  serviceName,
937
- "timed out",
924
+ "timeOut",
938
925
  )
939
926
 
940
- audit("AgentTaskFailed", {
941
- data: {
942
- taskId,
943
- contextId,
944
- service: serviceName,
945
- error: err.message,
946
- errorCode: "timeout",
947
- task: requestContext.task,
948
- },
949
- })
950
-
951
- eventBus.publish({
952
- kind: "status-update",
953
- taskId,
954
- contextId,
955
- status: {
956
- state: "canceled",
957
- message: agentMessage(summary),
958
- timestamp: new Date().toISOString(),
959
- },
960
- final: true,
961
- })
927
+ publishTimeoutHitl({ requestContext, eventBus, description: summary, serviceName })
962
928
  return
963
929
  }
964
930
 
965
931
  // Quota exceeded — summarize partial work instead of raw error
966
932
  if (err.quotaExceeded) {
967
- LOG.warn("quota exceeded", {
933
+ LOG.warn(serviceName, "-", "quota exceeded", {
968
934
  conversation: short(contextId),
969
- service: serviceName,
970
935
  error: err.message,
971
936
  })
972
937
 
973
938
  if (wfSpan) wfSpan.setAttribute("agent.outcome", "quota_exceeded")
974
939
  metrics.errorsTotal.add(1, { ...mAttrs, "agent.error.code": "quota_exceeded" })
975
940
 
976
- const summary = await this._summarizePartialWork(
977
- taskId,
978
- contextId,
979
- serviceName,
980
- "quota exceeded",
981
- )
941
+ const summary = await this._summarizePartialWork(taskId, contextId, serviceName, "quota")
982
942
 
983
943
  audit("AgentTaskFailed", {
984
944
  data: {
@@ -1005,16 +965,11 @@ class GraphExecutor {
1005
965
  return
1006
966
  }
1007
967
 
1008
- LOG.error("failed", {
1009
- conversation: short(contextId),
1010
- service: serviceName,
1011
- error: err.message,
1012
- })
1013
- LOG.debug("failed stack", {
1014
- conversation: short(contextId),
1015
- service: serviceName,
1016
- stack: err.stack,
1017
- })
968
+ LOG.error(
969
+ Object.assign(err, {
970
+ conversation: short(contextId),
971
+ }),
972
+ )
1018
973
 
1019
974
  if (wfSpan) {
1020
975
  wfSpan.setAttribute("agent.outcome", "failed")
@@ -67,7 +67,7 @@ export default function registerDefaultAgentHandlers(srv) {
67
67
  }
68
68
 
69
69
  const { buildMcpTools } = await import("./mcp-tools.js")
70
- const { buildSubAgentTool } = await import("./sub-agent-tools.js")
70
+ const { buildSubAgentTool } = await import("./subagent-tools.js")
71
71
 
72
72
  const results = await Promise.allSettled([
73
73
  ...mcpEntries.map((e) => buildMcpTools(e.service ?? e)),
@@ -76,7 +76,7 @@ export default function registerDefaultAgentHandlers(srv) {
76
76
 
77
77
  const extraTools = []
78
78
  for (const r of results) {
79
- // MCP connections yield an array of tools; sub-agent connections yield a
79
+ // MCP connections yield an array of tools; subagent connections yield a
80
80
  // single tool. Normalize both so instrumentTools sees a flat tool list.
81
81
  if (r.status === "fulfilled") {
82
82
  if (Array.isArray(r.value)) extraTools.push(...r.value.filter(Boolean))
@@ -101,7 +101,7 @@ export async function buildMcpToolsFromConnection(serviceName) {
101
101
 
102
102
  const path = typeof credentials === "object" ? credentials?.path : null
103
103
  const mcpUrl = url.replace(/\/$/, "") + (path ? `/${path.replace(/^\//, "")}` : "")
104
- LOG.info(`Connecting to MCP server at ${mcpUrl}`)
104
+ LOG.info(`Connecting to MCP service ${serviceName}`, { at: mcpUrl })
105
105
 
106
106
  const resolveHeaders = async () => {
107
107
  if (destinationName) {
@@ -113,7 +113,8 @@ export async function buildMcpToolsFromConnection(serviceName) {
113
113
  return token ? { Authorization: `Bearer ${token}` } : {}
114
114
  }
115
115
 
116
- return { _mcpDynamic: true, mcpUrl, serviceName, resolveHeaders }
116
+ const toolFilter = cds.requires[serviceName]?.mcp?.tools
117
+ return { _mcpDynamic: true, mcpUrl, serviceName, resolveHeaders, toolFilter }
117
118
  }
118
119
 
119
120
  export async function buildMcpTools(serviceName) {
@@ -1,10 +1,14 @@
1
1
  import cds from "@sap/cds"
2
2
  import { tool } from "@langchain/core/tools"
3
3
  import { z } from "zod"
4
+ import { getTracer } from "../../lib/telemetry/metrics.js"
4
5
  import { LangGraphExecutor } from "../langgraph-executor-srv.js"
5
6
  import { short, toolName } from "../../lib/utils/utils.js"
6
7
 
7
- const LOG = cds.log("agents:sub-agents|agents|sub-agents")
8
+ const LOG = cds.log("agents:a2a|agents|subagents|a2a")
9
+
10
+ const TRUNCATE = cds.env.agents?.truncate || 111
11
+ const truncated = (msg) => (msg?.length > TRUNCATE ? msg.slice(0, TRUNCATE) + "..." : msg)
8
12
 
9
13
  import { inspect } from "util"
10
14
  /**
@@ -93,10 +97,14 @@ function createA2ATool(client, agentCard) {
93
97
  LOG.trace(`Raw results from ${subagent}`, inspect(result, { depth: null, colors: true }))
94
98
  let response = formatToolResult(extractResult(result))
95
99
  if (response)
96
- LOG.info(`Got response from ${subagent}`, { messageId }, "\n\n" + response + "\n")
100
+ LOG.info(
101
+ `Got response from ${subagent}`,
102
+ { messageId },
103
+ "\n\n" + truncated(response) + "\n",
104
+ )
97
105
  return response
98
106
  } catch (err) {
99
- LOG.warn("Sub agent tool error", { subagent, error: err.message })
107
+ LOG.warn("Subagent tool error", { subagent, error: err.message })
100
108
  return `Error communicating with ${subagent}: ${err.message}`
101
109
  }
102
110
  },
@@ -112,13 +120,13 @@ function createA2ATool(client, agentCard) {
112
120
 
113
121
  export async function buildSubAgentToolLocally(serviceName) {
114
122
  const srv = cds.services[serviceName]
115
- if (!srv) throw new Error(`[sub-agents] No local service "${serviceName}" found.`)
123
+ if (!srv) throw new Error(`[subagents] No local service "${serviceName}" found.`)
116
124
 
117
125
  const executor = LangGraphExecutor.for(srv)
118
126
 
119
127
  const { generateAgentCard } = await import("../../lib/protocol/agent-card.js")
120
128
  const agentCard = generateAgentCard(srv)
121
- LOG.info(`Connecting to sub agent ${serviceName}`, "(local)")
129
+ LOG.info(`Connecting to subagent ${serviceName}`, "(local)")
122
130
 
123
131
  const { RequestContext, DefaultExecutionEventBus } = await import("@a2a-js/sdk/server")
124
132
 
@@ -147,7 +155,7 @@ export async function buildSubAgentToolLocally(serviceName) {
147
155
  .map((p) => p.text)
148
156
  .join("\n")
149
157
  if (text) statusText = text
150
- if (state === "failed") failed = text || "Sub-agent execution failed."
158
+ if (state === "failed") failed = text || "Subagent execution failed."
151
159
  } else if (event.kind === "artifact-update") {
152
160
  const parts = event.artifact?.parts || []
153
161
  if (event.artifact?.artifactId === "response") {
@@ -176,19 +184,17 @@ export async function buildSubAgentToolLocally(serviceName) {
176
184
  taskId,
177
185
  contextId,
178
186
  )
179
- const truncated = message?.length > 80 ? message.slice(0, 80) + "..." : message
180
187
 
181
188
  try {
182
- // Run the sub-agent detached from the calling agent, in its own root
189
+ // Run the subagent detached from the calling agent, in its own root
183
190
  // context and transaction (cds.spawn creates + commits a fresh tx). A
184
191
  // shared transaction breaks the stream.
185
192
  await new Promise((resolve, reject) => {
186
193
  cds
187
194
  .spawn({ user: cds.context?.user, tenant: cds.context?.tenant }, async () => {
188
- LOG.info("request", {
195
+ LOG.info(srv.name, "-", "request", {
189
196
  conversation: short(contextId),
190
- service: srv.name,
191
- text: truncated,
197
+ text: truncated(message),
192
198
  })
193
199
 
194
200
  await executor.execute(requestContext, eventBus)
@@ -198,7 +204,7 @@ export async function buildSubAgentToolLocally(serviceName) {
198
204
  .on("failed", reject)
199
205
  })
200
206
  } catch (err) {
201
- LOG.warn("Local sub-agent tool error", { agent: agentCard.name, error: err.message })
207
+ LOG.warn("Local subagent tool error", { agent: agentCard.name, error: err.message })
202
208
  return `Error running ${agentCard.name}: ${err.message}`
203
209
  }
204
210
 
@@ -238,7 +244,7 @@ export async function buildSubAgentToolFromConnection(serviceName) {
238
244
 
239
245
  if (!localUrl && !destinationName) {
240
246
  throw new Error(
241
- `[sub-agents] Could not resolve URL or destination name for service "${serviceName}". Check cds.requires config.`,
247
+ `[subagents] Could not resolve URL or destination name for service "${serviceName}". Check cds.requires config.`,
242
248
  )
243
249
  }
244
250
 
@@ -286,13 +292,13 @@ export async function buildSubAgentToolFromConnection(serviceName) {
286
292
 
287
293
  if (!agentBaseUrl) {
288
294
  throw new Error(
289
- `[sub-agents] Could not resolve URL for service "${serviceName}" after destination lookup.`,
295
+ `[subagents] Could not resolve URL for service "${serviceName}" after destination lookup.`,
290
296
  )
291
297
  }
292
298
 
293
299
  const path = typeof credentials === "object" ? credentials?.path : null
294
300
  const base = agentBaseUrl.replace(/\/$/, "") + (path ? `/${path.replace(/^\//, "")}` : "")
295
- LOG.info(`Connecting to sub agent ${serviceName}`, { at: base })
301
+ LOG.info(`Connecting to subagent ${serviceName}`, { at: base })
296
302
 
297
303
  // revisit: a2a agents may be tenant specific, card per tenant?
298
304
  const initialHeaders = await resolveHeaders()
@@ -302,7 +308,7 @@ export async function buildSubAgentToolFromConnection(serviceName) {
302
308
  })
303
309
  if (!cardRes.ok) {
304
310
  throw new Error(
305
- `[sub-agents] Agent card fetch failed for "${serviceName}" at ${cardUrl}: HTTP ${cardRes.status}`,
311
+ `[subagents] Agent card fetch failed for "${serviceName}" at ${cardUrl}: HTTP ${cardRes.status}`,
306
312
  )
307
313
  }
308
314
  const agentCard = await cardRes.json()
@@ -312,6 +318,10 @@ export async function buildSubAgentToolFromConnection(serviceName) {
312
318
 
313
319
  const customFetch = async (url, init = {}) => {
314
320
  const headers = await resolveHeaders()
321
+ if (getTracer()) {
322
+ const { context, propagation } = await import("@opentelemetry/api")
323
+ propagation.inject(context.active(), headers)
324
+ }
315
325
  return fetch(url, { ...init, headers: { ...headers, ...(init.headers || {}) } })
316
326
  }
317
327
  const factory = new ClientFactory(
@@ -11,7 +11,7 @@ import {
11
11
  executeCallActionTool,
12
12
  executePerActionTool,
13
13
  } from "@cap-js/mcp/lib/tools.js"
14
- import { getFilteredEntities, getFilteredActions, getAgentLogger } from "../../lib/utils/utils.js"
14
+ import { getFilteredEntities, getFilteredActions } from "../../lib/utils/utils.js"
15
15
  import { isTextMime } from "../../lib/agents/markdown/backends/mime-utils.js"
16
16
  import { checkAuthorization } from "@cap-js/mcp/lib/auth.js"
17
17
 
@@ -31,7 +31,6 @@ function cachedAuth(srv) {
31
31
 
32
32
  class GenericReadTool extends DynamicStructuredTool {
33
33
  constructor(srv, entities) {
34
- const log = getAgentLogger(srv)
35
34
  const def = createGenericReadToolDefinition(Object.keys(entities), srv.name, "")
36
35
  super({
37
36
  name: def.name,
@@ -39,7 +38,7 @@ class GenericReadTool extends DynamicStructuredTool {
39
38
  schema: def.inputSchema,
40
39
  responseFormat: "content_and_artifact",
41
40
  func: async (args) => {
42
- return unwrap(await executeGenericReadTool(srv, entities, args, { log }))
41
+ return unwrap(await executeGenericReadTool(srv, entities, args))
43
42
  },
44
43
  })
45
44
  this.srv = srv
@@ -68,7 +67,6 @@ class GenericReadTool extends DynamicStructuredTool {
68
67
 
69
68
  class DescribeTool extends DynamicStructuredTool {
70
69
  constructor(srv, entities, actions) {
71
- const log = getAgentLogger(srv)
72
70
  const def = createDescribeToolDefinition(
73
71
  Object.keys(entities),
74
72
  Object.keys(actions),
@@ -81,7 +79,7 @@ class DescribeTool extends DynamicStructuredTool {
81
79
  schema: def.inputSchema,
82
80
  responseFormat: "content_and_artifact",
83
81
  func: async (args) => {
84
- return unwrap(await executeDescribe(srv, entities, actions, args, { log }))
82
+ return unwrap(await executeDescribe(srv, entities, actions, args))
85
83
  },
86
84
  })
87
85
  this.srv = srv
@@ -121,7 +119,6 @@ class DescribeTool extends DynamicStructuredTool {
121
119
 
122
120
  class PerActionTool extends DynamicStructuredTool {
123
121
  constructor(srv, actionName, action) {
124
- const log = getAgentLogger(srv)
125
122
  const def = createPerActionToolDefinition(actionName, action, srv.name, srv.model, "")
126
123
  super({
127
124
  name: def.name,
@@ -129,7 +126,7 @@ class PerActionTool extends DynamicStructuredTool {
129
126
  schema: def.inputSchema,
130
127
  responseFormat: "content_and_artifact",
131
128
  func: async (args) => {
132
- return unwrap(await executePerActionTool(srv, actionName, action, args, { log }))
129
+ return unwrap(await executePerActionTool(srv, actionName, action, args))
133
130
  },
134
131
  })
135
132
  this.srv = srv
@@ -145,7 +142,6 @@ class PerActionTool extends DynamicStructuredTool {
145
142
 
146
143
  class CallActionTool extends DynamicStructuredTool {
147
144
  constructor(srv, actions) {
148
- const log = getAgentLogger(srv)
149
145
  const def = createCallActionToolDefinition(Object.keys(actions), srv.name, "")
150
146
  super({
151
147
  name: def.name,
@@ -153,7 +149,7 @@ class CallActionTool extends DynamicStructuredTool {
153
149
  schema: def.inputSchema,
154
150
  responseFormat: "content_and_artifact",
155
151
  func: async (args) => {
156
- return unwrap(await executeCallActionTool(srv, actions, args, { log }))
152
+ return unwrap(await executeCallActionTool(srv, actions, args))
157
153
  },
158
154
  })
159
155
  this.srv = srv