@struct-ai/sdk 0.1.0
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/LICENSE +201 -0
- package/README.md +168 -0
- package/dist/commonjs/content-capture.d.ts +10 -0
- package/dist/commonjs/content-capture.js +23 -0
- package/dist/commonjs/context.d.ts +30 -0
- package/dist/commonjs/context.js +94 -0
- package/dist/commonjs/core.d.ts +120 -0
- package/dist/commonjs/core.js +408 -0
- package/dist/commonjs/events.d.ts +12 -0
- package/dist/commonjs/events.js +103 -0
- package/dist/commonjs/index.d.ts +6 -0
- package/dist/commonjs/index.js +10 -0
- package/dist/commonjs/integrations/anthropic-content.d.ts +24 -0
- package/dist/commonjs/integrations/anthropic-content.js +178 -0
- package/dist/commonjs/integrations/anthropic.d.ts +34 -0
- package/dist/commonjs/integrations/anthropic.js +377 -0
- package/dist/commonjs/integrations/index.d.ts +5 -0
- package/dist/commonjs/integrations/index.js +47 -0
- package/dist/commonjs/integrations/langchain-callback.d.ts +134 -0
- package/dist/commonjs/integrations/langchain-callback.js +723 -0
- package/dist/commonjs/integrations/langchain-content.d.ts +35 -0
- package/dist/commonjs/integrations/langchain-content.js +307 -0
- package/dist/commonjs/integrations/langchain.d.ts +11 -0
- package/dist/commonjs/integrations/langchain.js +100 -0
- package/dist/commonjs/package.json +3 -0
- package/dist/commonjs/semconv.d.ts +54 -0
- package/dist/commonjs/semconv.js +74 -0
- package/dist/commonjs/truncation.d.ts +10 -0
- package/dist/commonjs/truncation.js +103 -0
- package/dist/esm/content-capture.d.ts +10 -0
- package/dist/esm/content-capture.js +17 -0
- package/dist/esm/context.d.ts +30 -0
- package/dist/esm/context.js +80 -0
- package/dist/esm/core.d.ts +120 -0
- package/dist/esm/core.js +403 -0
- package/dist/esm/events.d.ts +12 -0
- package/dist/esm/events.js +99 -0
- package/dist/esm/index.d.ts +6 -0
- package/dist/esm/index.js +5 -0
- package/dist/esm/integrations/anthropic-content.d.ts +24 -0
- package/dist/esm/integrations/anthropic-content.js +168 -0
- package/dist/esm/integrations/anthropic.d.ts +34 -0
- package/dist/esm/integrations/anthropic.js +370 -0
- package/dist/esm/integrations/index.d.ts +5 -0
- package/dist/esm/integrations/index.js +42 -0
- package/dist/esm/integrations/langchain-callback.d.ts +134 -0
- package/dist/esm/integrations/langchain-callback.js +719 -0
- package/dist/esm/integrations/langchain-content.d.ts +35 -0
- package/dist/esm/integrations/langchain-content.js +294 -0
- package/dist/esm/integrations/langchain.d.ts +11 -0
- package/dist/esm/integrations/langchain.js +95 -0
- package/dist/esm/package.json +3 -0
- package/dist/esm/semconv.d.ts +54 -0
- package/dist/esm/semconv.js +71 -0
- package/dist/esm/truncation.d.ts +10 -0
- package/dist/esm/truncation.js +96 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/content-capture.d.ts +10 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/context.d.ts +30 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/core.d.ts +120 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/events.d.ts +12 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/index.d.ts +6 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/anthropic-content.d.ts +24 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/anthropic.d.ts +34 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/index.d.ts +5 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/langchain-callback.d.ts +134 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/langchain-content.d.ts +35 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/integrations/langchain.d.ts +11 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/package.json +3 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/semconv.d.ts +54 -0
- package/dist/node_modules/@struct-ai/sdk/dist/commonjs/truncation.d.ts +10 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/content-capture.d.ts +10 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/context.d.ts +30 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/core.d.ts +120 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/events.d.ts +12 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/index.d.ts +6 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/anthropic-content.d.ts +24 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/anthropic.d.ts +34 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/index.d.ts +5 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/langchain-callback.d.ts +134 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/langchain-content.d.ts +35 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/integrations/langchain.d.ts +11 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/package.json +3 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/semconv.d.ts +54 -0
- package/dist/node_modules/@struct-ai/sdk/dist/esm/truncation.d.ts +10 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/dist/commonjs/package.json +3 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/dist/esm/package.json +3 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/package.json +103 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/anthropic/package.json +118 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/package.json +916 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/package.json +188 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/api/package.json +96 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/api-logs/package.json +91 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/core/package.json +96 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/exporter-logs-otlp-proto/package.json +108 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/exporter-trace-otlp-proto/package.json +105 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/resources/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-logs/package.json +109 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-trace-base/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-trace-node/package.json +76 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/package.json +140 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/nock/package.json +89 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/tshy/package.json +81 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/typescript/package.json +120 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/node_modules/vitest/package.json +239 -0
- package/dist/node_modules/@struct-ai/sdk/dist/node_modules/@struct-ai/sdk/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/core.d.ts +244 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/error.d.ts +54 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/index.d.ts +188 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/package.json +103 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/pagination.d.ts +26 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/resource.d.ts +6 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/streaming.d.ts +41 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/uploads.d.ts +75 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@anthropic-ai/sdk/version.d.ts +2 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/anthropic/experimental.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/anthropic/index.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/anthropic/package.json +118 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/agents.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/caches.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/chat_history.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/context.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/documents.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/embeddings.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/example_selectors.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/index.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/indexing.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/load.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/memory.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/messages.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/output_parsers.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/outputs.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/package.json +916 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/prompt_values.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/prompts.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/retrievers.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/runnables.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/singletons.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/stores.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/structured_query.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/tools.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/core/vectorstores.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/index.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/package.json +188 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/prebuilt.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/pregel.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/remote.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/web.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@langchain/langgraph/zod.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/api/package.json +96 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/api-logs/package.json +91 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/core/package.json +96 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/exporter-logs-otlp-proto/package.json +108 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/exporter-trace-otlp-proto/package.json +105 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/resources/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-logs/package.json +109 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-trace-base/package.json +100 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@opentelemetry/sdk-trace-node/package.json +76 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/assert.d.ts +1062 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/async_hooks.d.ts +605 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/buffer.buffer.d.ts +471 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/buffer.d.ts +1936 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/child_process.d.ts +1475 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/cluster.d.ts +577 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/console.d.ts +452 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/constants.d.ts +21 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/crypto.d.ts +4590 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/dgram.d.ts +597 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/diagnostics_channel.d.ts +578 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/dns.d.ts +871 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/domain.d.ts +170 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/events.d.ts +977 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/fs.d.ts +4375 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/globals.d.ts +172 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/globals.typedarray.d.ts +38 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/http.d.ts +2049 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/http2.d.ts +2631 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/https.d.ts +578 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/index.d.ts +93 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/inspector.generated.d.ts +3966 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/module.d.ts +539 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/net.d.ts +1031 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/os.d.ts +506 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/package.json +140 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/path.d.ts +200 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/perf_hooks.d.ts +961 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/process.d.ts +1961 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/punycode.d.ts +117 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/querystring.d.ts +152 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/readline.d.ts +589 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/repl.d.ts +430 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/sea.d.ts +153 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/stream.d.ts +1698 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/string_decoder.d.ts +67 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/test.d.ts +1787 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/timers.d.ts +286 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/tls.d.ts +1259 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/trace_events.d.ts +197 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/tty.d.ts +208 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/url.d.ts +964 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/util.d.ts +2331 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/v8.d.ts +809 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/vm.d.ts +1001 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/wasi.d.ts +181 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/worker_threads.d.ts +715 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/@types/node/zlib.d.ts +598 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/nock/package.json +89 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/tshy/package.json +81 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/typescript/package.json +120 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/config.d.ts +3 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/coverage.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/environments.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/globals.d.ts +22 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/import-meta.d.ts +5 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/importMeta.d.ts +4 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/jsdom.d.ts +6 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/mocker.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/node.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/optional-runtime-types.d.ts +6 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/optional-types.d.ts +7 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/package.json +239 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/reporters.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/runners.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/snapshot.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/suite.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/node_modules/vitest/worker.d.ts +1 -0
- package/dist/node_modules/@struct-ai/sdk/package.json +100 -0
- package/package.json +100 -0
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
import { safeJsonStringify, truncateAndSerialize, truncateField, } from "../truncation.js";
|
|
2
|
+
import { ANTHROPIC_FINISH_REASON_MAP } from "../semconv.js";
|
|
3
|
+
/**
|
|
4
|
+
* Walk Anthropic response content blocks, return (name, id) pairs for tool_use blocks.
|
|
5
|
+
* Port of _iter_tool_uses from anthropic.py.
|
|
6
|
+
*/
|
|
7
|
+
export function iterToolUses(blocks) {
|
|
8
|
+
const out = [];
|
|
9
|
+
if (!Array.isArray(blocks))
|
|
10
|
+
return out;
|
|
11
|
+
for (const block of blocks) {
|
|
12
|
+
if (!block || typeof block !== "object")
|
|
13
|
+
continue;
|
|
14
|
+
const b = block;
|
|
15
|
+
if (b.type !== "tool_use")
|
|
16
|
+
continue;
|
|
17
|
+
const name = typeof b.name === "string" ? b.name : "";
|
|
18
|
+
const id = typeof b.id === "string" ? b.id : "";
|
|
19
|
+
if (name && id)
|
|
20
|
+
out.push([name, id]);
|
|
21
|
+
}
|
|
22
|
+
return out;
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Convert arbitrary content (string | block[] | unknown) → GenAI parts.
|
|
26
|
+
* Port of _content_to_parts from anthropic.py.
|
|
27
|
+
*/
|
|
28
|
+
export function contentToParts(content) {
|
|
29
|
+
if (content == null)
|
|
30
|
+
return [];
|
|
31
|
+
if (typeof content === "string") {
|
|
32
|
+
return [{ type: "text", content }];
|
|
33
|
+
}
|
|
34
|
+
if (!Array.isArray(content)) {
|
|
35
|
+
return [{ type: "text", content: String(content) }];
|
|
36
|
+
}
|
|
37
|
+
const parts = [];
|
|
38
|
+
for (const item of content) {
|
|
39
|
+
if (item == null)
|
|
40
|
+
continue;
|
|
41
|
+
if (typeof item === "string") {
|
|
42
|
+
parts.push({ type: "text", content: item });
|
|
43
|
+
continue;
|
|
44
|
+
}
|
|
45
|
+
if (typeof item !== "object")
|
|
46
|
+
continue;
|
|
47
|
+
const block = item;
|
|
48
|
+
const blockType = typeof block.type === "string" ? block.type : undefined;
|
|
49
|
+
if (blockType === "text") {
|
|
50
|
+
const text = typeof block.text === "string" ? block.text : "";
|
|
51
|
+
parts.push({ type: "text", content: text });
|
|
52
|
+
}
|
|
53
|
+
else if (blockType === "tool_use") {
|
|
54
|
+
const name = typeof block.name === "string" ? block.name : "";
|
|
55
|
+
const part = { type: "tool_call", name };
|
|
56
|
+
if (block.id)
|
|
57
|
+
part.id = block.id;
|
|
58
|
+
if (block.input !== undefined)
|
|
59
|
+
part.arguments = block.input;
|
|
60
|
+
parts.push(part);
|
|
61
|
+
}
|
|
62
|
+
else if (blockType === "tool_result") {
|
|
63
|
+
const part = { type: "tool_call_response" };
|
|
64
|
+
if (block.tool_use_id)
|
|
65
|
+
part.id = block.tool_use_id;
|
|
66
|
+
part.response = block.content ?? "";
|
|
67
|
+
parts.push(part);
|
|
68
|
+
}
|
|
69
|
+
else if (blockType === "thinking") {
|
|
70
|
+
const thinking = typeof block.thinking === "string" ? block.thinking : "";
|
|
71
|
+
parts.push({ type: "reasoning", content: thinking });
|
|
72
|
+
}
|
|
73
|
+
else if (blockType === "image") {
|
|
74
|
+
const source = block.source ?? {};
|
|
75
|
+
if (source.type === "base64" && typeof source.data === "string") {
|
|
76
|
+
parts.push({
|
|
77
|
+
type: "blob",
|
|
78
|
+
modality: "image",
|
|
79
|
+
content: source.data.slice(0, 256) + "...",
|
|
80
|
+
mime_type: source.media_type,
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
else if (source.type === "url" && typeof source.url === "string") {
|
|
84
|
+
parts.push({
|
|
85
|
+
type: "uri",
|
|
86
|
+
modality: "image",
|
|
87
|
+
uri: source.url,
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
else {
|
|
91
|
+
parts.push({ type: "image" });
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
else {
|
|
95
|
+
parts.push({ type: blockType || "unknown" });
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
return parts;
|
|
99
|
+
}
|
|
100
|
+
/** Convert Anthropic message list → GenAI input-messages JSON string. */
|
|
101
|
+
export function toInputMessages(messages) {
|
|
102
|
+
if (!Array.isArray(messages))
|
|
103
|
+
return "[]";
|
|
104
|
+
try {
|
|
105
|
+
const result = messages.map((msg) => {
|
|
106
|
+
const m = (msg ?? {});
|
|
107
|
+
const role = typeof m.role === "string" ? m.role : "user";
|
|
108
|
+
const parts = contentToParts(m.content);
|
|
109
|
+
return { role, parts };
|
|
110
|
+
});
|
|
111
|
+
return truncateAndSerialize(result);
|
|
112
|
+
}
|
|
113
|
+
catch {
|
|
114
|
+
return "[]";
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
/** Convert response content blocks → GenAI output-messages JSON string. */
|
|
118
|
+
export function toOutputMessages(contentBlocks, stopReason) {
|
|
119
|
+
try {
|
|
120
|
+
const parts = contentToParts(contentBlocks);
|
|
121
|
+
const msg = { role: "assistant", parts };
|
|
122
|
+
if (stopReason) {
|
|
123
|
+
msg.finish_reason = ANTHROPIC_FINISH_REASON_MAP[stopReason] ?? stopReason;
|
|
124
|
+
}
|
|
125
|
+
return truncateAndSerialize([msg]);
|
|
126
|
+
}
|
|
127
|
+
catch {
|
|
128
|
+
return "[]";
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
/** Convert system prompt (string | block[]) → GenAI system_instructions JSON string. */
|
|
132
|
+
export function toSystemInstructions(system) {
|
|
133
|
+
try {
|
|
134
|
+
if (typeof system === "string") {
|
|
135
|
+
return truncateAndSerialize([{ type: "text", content: system }]);
|
|
136
|
+
}
|
|
137
|
+
if (Array.isArray(system)) {
|
|
138
|
+
const parts = contentToParts(system);
|
|
139
|
+
return truncateAndSerialize(parts);
|
|
140
|
+
}
|
|
141
|
+
return "[]";
|
|
142
|
+
}
|
|
143
|
+
catch {
|
|
144
|
+
return "[]";
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
export function safeJsonForTool(obj) {
|
|
148
|
+
try {
|
|
149
|
+
return truncateAndSerialize(obj);
|
|
150
|
+
}
|
|
151
|
+
catch {
|
|
152
|
+
return safeJsonStringify(obj);
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
/** Extract the last user message's parts for parent-span propagation. */
|
|
156
|
+
export function lastUserMessageParts(messages) {
|
|
157
|
+
if (!Array.isArray(messages))
|
|
158
|
+
return undefined;
|
|
159
|
+
for (let i = messages.length - 1; i >= 0; i--) {
|
|
160
|
+
const msg = messages[i];
|
|
161
|
+
if (msg && msg.role === "user") {
|
|
162
|
+
return contentToParts(msg.content);
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
return undefined;
|
|
166
|
+
}
|
|
167
|
+
export { truncateField };
|
|
168
|
+
//# sourceMappingURL=anthropic-content.js.map
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { type Tracer } from "@opentelemetry/api";
|
|
2
|
+
import type { Logger } from "@opentelemetry/api-logs";
|
|
3
|
+
import { type StructSDK } from "../core.js";
|
|
4
|
+
interface PatchContext {
|
|
5
|
+
tracer: Tracer;
|
|
6
|
+
sdk: StructSDK;
|
|
7
|
+
logger: Logger | undefined;
|
|
8
|
+
}
|
|
9
|
+
interface CreateParams {
|
|
10
|
+
model?: string;
|
|
11
|
+
max_tokens?: number;
|
|
12
|
+
temperature?: number;
|
|
13
|
+
top_p?: number;
|
|
14
|
+
top_k?: number;
|
|
15
|
+
stop_sequences?: string[];
|
|
16
|
+
messages?: unknown[];
|
|
17
|
+
system?: unknown;
|
|
18
|
+
tools?: unknown[];
|
|
19
|
+
stream?: boolean;
|
|
20
|
+
}
|
|
21
|
+
export declare function patch(sdk: StructSDK): Promise<void>;
|
|
22
|
+
export declare function unpatch(): Promise<void>;
|
|
23
|
+
type CreateMethod = (this: unknown, params: CreateParams, opts?: unknown) => unknown;
|
|
24
|
+
type StreamMethod = (this: unknown, params: CreateParams, opts?: unknown) => unknown;
|
|
25
|
+
/** @internal */
|
|
26
|
+
export type _PatchContextForTest = PatchContext;
|
|
27
|
+
/** @internal */
|
|
28
|
+
export declare function _wrapCreateForTest(original: CreateMethod): CreateMethod;
|
|
29
|
+
/** @internal */
|
|
30
|
+
export declare function _wrapStreamForTest(original: StreamMethod): StreamMethod;
|
|
31
|
+
/** @internal */
|
|
32
|
+
export declare function _setActivePatchCtxForTest(ctx: PatchContext | undefined): void;
|
|
33
|
+
export {};
|
|
34
|
+
//# sourceMappingURL=anthropic.d.ts.map
|
|
@@ -0,0 +1,370 @@
|
|
|
1
|
+
import { SpanKind, SpanStatusCode, context as otelContext, trace, } from "@opentelemetry/api";
|
|
2
|
+
import { ensurePendingToolCallsSlot, getAgentSpan, getSessionId, pushPendingToolCalls, runWithStore, snapshotStore, } from "../context.js";
|
|
3
|
+
function childParentContext() {
|
|
4
|
+
const agentSpan = getAgentSpan();
|
|
5
|
+
return agentSpan
|
|
6
|
+
? trace.setSpan(otelContext.active(), agentSpan)
|
|
7
|
+
: otelContext.active();
|
|
8
|
+
}
|
|
9
|
+
import { safe } from "../core.js";
|
|
10
|
+
import { emitAnthropicChoiceEvent, emitAnthropicMessageEvents, } from "../events.js";
|
|
11
|
+
import { ERROR_TYPE, GEN_AI, STRUCT, } from "../semconv.js";
|
|
12
|
+
import { truncateAndSerialize } from "../truncation.js";
|
|
13
|
+
import { iterToolUses, lastUserMessageParts, safeJsonForTool, toInputMessages, toOutputMessages, toSystemInstructions, } from "./anthropic-content.js";
|
|
14
|
+
const STRUCT_WRAPPED = Symbol.for("struct.wrapped");
|
|
15
|
+
const STRUCT_ORIGINAL = Symbol.for("struct.original");
|
|
16
|
+
/**
|
|
17
|
+
* Mutable reference updated on each patch() call. Wrappers dereference this
|
|
18
|
+
* at call time, so the most recently initialized SDK always wins — matches
|
|
19
|
+
* the fact that `struct` is a singleton in production, and keeps tests with
|
|
20
|
+
* multiple StructSDK instances working correctly.
|
|
21
|
+
*/
|
|
22
|
+
const activePatchCtx = { value: undefined };
|
|
23
|
+
export async function patch(sdk) {
|
|
24
|
+
const anthropicMod = (await import("@anthropic-ai/sdk"));
|
|
25
|
+
activePatchCtx.value = {
|
|
26
|
+
tracer: sdk.getTracer("struct-sdk-anthropic"),
|
|
27
|
+
sdk,
|
|
28
|
+
logger: sdk.emitEvents ? sdk.getLogger("struct-sdk-anthropic") : undefined,
|
|
29
|
+
};
|
|
30
|
+
const classes = collectMessagesClasses(anthropicMod);
|
|
31
|
+
for (const cls of classes) {
|
|
32
|
+
wrapMethod(cls.prototype, "create", false);
|
|
33
|
+
wrapMethod(cls.prototype, "stream", true);
|
|
34
|
+
}
|
|
35
|
+
// Best-effort: also patch bedrock + vertex packages if installed.
|
|
36
|
+
await tryPatchCompanion("@anthropic-ai/bedrock-sdk");
|
|
37
|
+
await tryPatchCompanion("@anthropic-ai/vertex-sdk");
|
|
38
|
+
}
|
|
39
|
+
export async function unpatch() {
|
|
40
|
+
activePatchCtx.value = undefined;
|
|
41
|
+
try {
|
|
42
|
+
const anthropicMod = (await import("@anthropic-ai/sdk"));
|
|
43
|
+
const classes = collectMessagesClasses(anthropicMod);
|
|
44
|
+
for (const cls of classes) {
|
|
45
|
+
restoreMethod(cls.prototype, "create");
|
|
46
|
+
restoreMethod(cls.prototype, "stream");
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
catch {
|
|
50
|
+
/* not installed */
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
function collectMessagesClasses(mod) {
|
|
54
|
+
const classes = [];
|
|
55
|
+
const Anthropic = mod.default ?? mod.Anthropic;
|
|
56
|
+
if (typeof Anthropic === "function") {
|
|
57
|
+
const ctor = Anthropic;
|
|
58
|
+
if (typeof ctor.Messages === "function") {
|
|
59
|
+
classes.push(ctor.Messages);
|
|
60
|
+
}
|
|
61
|
+
if (ctor.Beta && typeof ctor.Beta.Messages === "function") {
|
|
62
|
+
classes.push(ctor.Beta.Messages);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
return classes;
|
|
66
|
+
}
|
|
67
|
+
async function tryPatchCompanion(moduleName) {
|
|
68
|
+
try {
|
|
69
|
+
const mod = (await import(moduleName));
|
|
70
|
+
const classes = collectMessagesClasses(mod);
|
|
71
|
+
for (const cls of classes) {
|
|
72
|
+
wrapMethod(cls.prototype, "create", false);
|
|
73
|
+
wrapMethod(cls.prototype, "stream", true);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
catch {
|
|
77
|
+
/* not installed */
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
function wrapMethod(proto, methodName, isStream) {
|
|
81
|
+
const original = proto[methodName];
|
|
82
|
+
if (typeof original !== "function")
|
|
83
|
+
return;
|
|
84
|
+
const existing = original;
|
|
85
|
+
if (existing[STRUCT_WRAPPED])
|
|
86
|
+
return;
|
|
87
|
+
const wrapper = isStream
|
|
88
|
+
? wrapStream(original)
|
|
89
|
+
: wrapCreate(original);
|
|
90
|
+
wrapper[STRUCT_WRAPPED] = true;
|
|
91
|
+
wrapper[STRUCT_ORIGINAL] = original;
|
|
92
|
+
proto[methodName] = wrapper;
|
|
93
|
+
}
|
|
94
|
+
function restoreMethod(proto, methodName) {
|
|
95
|
+
const current = proto[methodName];
|
|
96
|
+
if (current && current[STRUCT_WRAPPED] && current[STRUCT_ORIGINAL]) {
|
|
97
|
+
proto[methodName] = current[STRUCT_ORIGINAL];
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
function wrapCreate(original) {
|
|
101
|
+
return function wrappedCreate(params, opts) {
|
|
102
|
+
const patchCtx = activePatchCtx.value;
|
|
103
|
+
if (!patchCtx) {
|
|
104
|
+
return original.call(this, params, opts);
|
|
105
|
+
}
|
|
106
|
+
// If params.stream is true, Messages.create delegates to the streaming path.
|
|
107
|
+
// We still need to instrument the returned stream like we do in messages.stream.
|
|
108
|
+
if (params && params.stream === true) {
|
|
109
|
+
return wrapStream(original).call(this, params, opts);
|
|
110
|
+
}
|
|
111
|
+
const { tracer, sdk, logger } = patchCtx;
|
|
112
|
+
const internalLogger = sdk.getInternalLogger();
|
|
113
|
+
const model = params?.model ?? "unknown";
|
|
114
|
+
// Span creation itself can fail (custom tracer, broken context). If it
|
|
115
|
+
// does, fall through to calling `original` directly so the user's API
|
|
116
|
+
// call always runs. Mirrors the Python `_wrap_create` fall-through.
|
|
117
|
+
let span;
|
|
118
|
+
let ctx;
|
|
119
|
+
safe(() => {
|
|
120
|
+
const parentCtx = childParentContext();
|
|
121
|
+
span = tracer.startSpan(`chat ${model}`, { kind: SpanKind.CLIENT }, parentCtx);
|
|
122
|
+
ctx = trace.setSpan(parentCtx, span);
|
|
123
|
+
}, "anthropic.create.start_span", internalLogger);
|
|
124
|
+
if (!span || !ctx) {
|
|
125
|
+
return original.call(this, params, opts);
|
|
126
|
+
}
|
|
127
|
+
const liveSpan = span;
|
|
128
|
+
const liveCtx = ctx;
|
|
129
|
+
// Enter the span's context BEFORE emitting request-side log records so
|
|
130
|
+
// `logger.emit({ context: otelContext.active() })` picks up the chat
|
|
131
|
+
// span as the log's TraceId / SpanId. Without this the UI can't link
|
|
132
|
+
// user/system message logs back to the chat span.
|
|
133
|
+
return otelContext.with(liveCtx, () => {
|
|
134
|
+
safe(() => setChatRequestAttrs(liveSpan, params, sdk, logger), "anthropic.create.set_request_attrs", internalLogger);
|
|
135
|
+
const promise = Promise.resolve(original.call(this, params, opts));
|
|
136
|
+
return promise.then((result) => {
|
|
137
|
+
safe(() => setChatResponseAttrs(liveSpan, sdk, result, logger), "anthropic.create.set_response_attrs", internalLogger);
|
|
138
|
+
safe(() => liveSpan.setStatus({ code: SpanStatusCode.OK }), "anthropic.create.set_ok_status", internalLogger);
|
|
139
|
+
safe(() => liveSpan.end(), "anthropic.create.span_end", internalLogger);
|
|
140
|
+
return result;
|
|
141
|
+
}, (err) => {
|
|
142
|
+
safe(() => recordErrorOnSpan(liveSpan, err), "anthropic.create.record_error", internalLogger);
|
|
143
|
+
safe(() => liveSpan.end(), "anthropic.create.span_end_on_error", internalLogger);
|
|
144
|
+
// User's API exception always propagates unchanged.
|
|
145
|
+
throw err;
|
|
146
|
+
});
|
|
147
|
+
});
|
|
148
|
+
};
|
|
149
|
+
}
|
|
150
|
+
function wrapStream(original) {
|
|
151
|
+
return function wrappedStream(params, opts) {
|
|
152
|
+
const patchCtx = activePatchCtx.value;
|
|
153
|
+
if (!patchCtx) {
|
|
154
|
+
return original.call(this, params, opts);
|
|
155
|
+
}
|
|
156
|
+
const { tracer, sdk, logger } = patchCtx;
|
|
157
|
+
const internalLogger = sdk.getInternalLogger();
|
|
158
|
+
const model = params?.model ?? "unknown";
|
|
159
|
+
// Span creation itself can fail. If it does, fall through to calling
|
|
160
|
+
// `original` directly so the user's stream call always runs. Mirrors
|
|
161
|
+
// the Python `_wrap_stream` fall-through pattern.
|
|
162
|
+
let span;
|
|
163
|
+
let ctx;
|
|
164
|
+
safe(() => {
|
|
165
|
+
const parentCtx = childParentContext();
|
|
166
|
+
span = tracer.startSpan(`chat ${model}`, { kind: SpanKind.CLIENT }, parentCtx);
|
|
167
|
+
ctx = trace.setSpan(parentCtx, span);
|
|
168
|
+
}, "anthropic.stream.start_span", internalLogger);
|
|
169
|
+
if (!span || !ctx) {
|
|
170
|
+
return original.call(this, params, opts);
|
|
171
|
+
}
|
|
172
|
+
const liveSpan = span;
|
|
173
|
+
const liveCtx = ctx;
|
|
174
|
+
const storeSnapshot = snapshotStore();
|
|
175
|
+
// Enter the span's context BEFORE request-side log emission so logs
|
|
176
|
+
// link back to the chat span via TraceId. Same rationale as wrapCreate.
|
|
177
|
+
// @anthropic-ai/sdk's `stream()` returns a MessageStream synchronously.
|
|
178
|
+
const stream = otelContext.with(liveCtx, () => {
|
|
179
|
+
safe(() => setChatRequestAttrs(liveSpan, params, sdk, logger), "anthropic.stream.set_request_attrs", internalLogger);
|
|
180
|
+
return original.call(this, params, opts);
|
|
181
|
+
});
|
|
182
|
+
let finalized = false;
|
|
183
|
+
const finalize = (result, err) => {
|
|
184
|
+
if (finalized)
|
|
185
|
+
return;
|
|
186
|
+
finalized = true;
|
|
187
|
+
runWithStore(storeSnapshot, () => {
|
|
188
|
+
if (err) {
|
|
189
|
+
safe(() => recordErrorOnSpan(liveSpan, err), "anthropic.stream.record_error", internalLogger);
|
|
190
|
+
}
|
|
191
|
+
else if (result) {
|
|
192
|
+
safe(() => otelContext.with(liveCtx, () => setChatResponseAttrs(liveSpan, sdk, result, logger)), "anthropic.stream.set_response_attrs", internalLogger);
|
|
193
|
+
safe(() => liveSpan.setStatus({ code: SpanStatusCode.OK }), "anthropic.stream.set_ok_status", internalLogger);
|
|
194
|
+
}
|
|
195
|
+
else {
|
|
196
|
+
safe(() => liveSpan.setStatus({ code: SpanStatusCode.OK }), "anthropic.stream.set_ok_status", internalLogger);
|
|
197
|
+
}
|
|
198
|
+
safe(() => liveSpan.end(), "anthropic.stream.span_end", internalLogger);
|
|
199
|
+
});
|
|
200
|
+
};
|
|
201
|
+
const ee = stream;
|
|
202
|
+
if (ee && typeof ee.on === "function") {
|
|
203
|
+
ee.on("finalMessage", (msg) => {
|
|
204
|
+
finalize(msg, undefined);
|
|
205
|
+
});
|
|
206
|
+
ee.on("error", (err) => {
|
|
207
|
+
finalize(undefined, err);
|
|
208
|
+
});
|
|
209
|
+
// If the stream is created and never iterated / finalized, at least
|
|
210
|
+
// don't hang on test exit — "end" fires after iteration completes.
|
|
211
|
+
ee.on("end", () => {
|
|
212
|
+
// Only fires if no finalMessage / error fired first (rare path).
|
|
213
|
+
finalize(undefined, undefined);
|
|
214
|
+
});
|
|
215
|
+
}
|
|
216
|
+
// Wrap the async iterator so each .next() runs inside the captured ALS store.
|
|
217
|
+
if (ee && typeof ee[Symbol.asyncIterator] === "function") {
|
|
218
|
+
const originalIter = ee[Symbol.asyncIterator].bind(ee);
|
|
219
|
+
ee[Symbol.asyncIterator] = () => {
|
|
220
|
+
const inner = originalIter();
|
|
221
|
+
const wrapped = {
|
|
222
|
+
next() {
|
|
223
|
+
return runWithStore(storeSnapshot, () => inner.next());
|
|
224
|
+
},
|
|
225
|
+
return(value) {
|
|
226
|
+
return runWithStore(storeSnapshot, () => inner.return ? inner.return(value) : Promise.resolve({ value, done: true }));
|
|
227
|
+
},
|
|
228
|
+
throw(err) {
|
|
229
|
+
return runWithStore(storeSnapshot, () => inner.throw
|
|
230
|
+
? inner.throw(err)
|
|
231
|
+
: Promise.reject(err));
|
|
232
|
+
},
|
|
233
|
+
};
|
|
234
|
+
return wrapped;
|
|
235
|
+
};
|
|
236
|
+
}
|
|
237
|
+
return stream;
|
|
238
|
+
};
|
|
239
|
+
}
|
|
240
|
+
function setChatRequestAttrs(span, params, sdk, logger) {
|
|
241
|
+
span.setAttribute(GEN_AI.OPERATION_NAME, "chat");
|
|
242
|
+
span.setAttribute(GEN_AI.PROVIDER_NAME, "anthropic");
|
|
243
|
+
const model = params?.model ?? "unknown";
|
|
244
|
+
span.setAttribute(GEN_AI.REQUEST_MODEL, model);
|
|
245
|
+
const sessionId = getSessionId();
|
|
246
|
+
if (sessionId) {
|
|
247
|
+
span.setAttribute(GEN_AI.CONVERSATION_ID, sessionId);
|
|
248
|
+
}
|
|
249
|
+
if (params?.max_tokens !== undefined) {
|
|
250
|
+
span.setAttribute(GEN_AI.REQUEST_MAX_TOKENS, params.max_tokens);
|
|
251
|
+
}
|
|
252
|
+
if (params?.temperature !== undefined) {
|
|
253
|
+
span.setAttribute(GEN_AI.REQUEST_TEMPERATURE, params.temperature);
|
|
254
|
+
}
|
|
255
|
+
if (params?.top_p !== undefined) {
|
|
256
|
+
span.setAttribute(GEN_AI.REQUEST_TOP_P, params.top_p);
|
|
257
|
+
}
|
|
258
|
+
if (params?.top_k !== undefined) {
|
|
259
|
+
span.setAttribute(GEN_AI.REQUEST_TOP_K, params.top_k);
|
|
260
|
+
}
|
|
261
|
+
if (params?.stop_sequences && params.stop_sequences.length > 0) {
|
|
262
|
+
span.setAttribute(GEN_AI.REQUEST_STOP_SEQUENCES, params.stop_sequences);
|
|
263
|
+
}
|
|
264
|
+
if (Array.isArray(params?.messages)) {
|
|
265
|
+
span.setAttribute(STRUCT.INPUT_MESSAGE_COUNT, params.messages.length);
|
|
266
|
+
propagateUserPromptToParent(params.messages);
|
|
267
|
+
}
|
|
268
|
+
if (sdk.emitEvents && logger && Array.isArray(params?.messages)) {
|
|
269
|
+
emitAnthropicMessageEvents(logger, params.messages, params.system);
|
|
270
|
+
}
|
|
271
|
+
if (sdk.emitSpanContent) {
|
|
272
|
+
if (Array.isArray(params?.messages)) {
|
|
273
|
+
span.setAttribute(GEN_AI.INPUT_MESSAGES, toInputMessages(params.messages));
|
|
274
|
+
}
|
|
275
|
+
if (params?.system) {
|
|
276
|
+
span.setAttribute(GEN_AI.SYSTEM_INSTRUCTIONS, toSystemInstructions(params.system));
|
|
277
|
+
}
|
|
278
|
+
if (params?.tools && Array.isArray(params.tools)) {
|
|
279
|
+
span.setAttribute(GEN_AI.TOOL_DEFINITIONS, safeJsonForTool(params.tools));
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
function setChatResponseAttrs(span, sdk, response, logger) {
|
|
284
|
+
const usage = response.usage;
|
|
285
|
+
if (usage) {
|
|
286
|
+
const inputTokens = usage.input_tokens ?? 0;
|
|
287
|
+
const outputTokens = usage.output_tokens ?? 0;
|
|
288
|
+
const cacheRead = usage.cache_read_input_tokens ?? 0;
|
|
289
|
+
const cacheCreation = usage.cache_creation_input_tokens ?? 0;
|
|
290
|
+
// Anthropic's input_tokens excludes cached tokens — add them back for the true total.
|
|
291
|
+
span.setAttribute(GEN_AI.USAGE_INPUT_TOKENS, inputTokens + cacheRead + cacheCreation);
|
|
292
|
+
span.setAttribute(GEN_AI.USAGE_OUTPUT_TOKENS, outputTokens);
|
|
293
|
+
if (cacheRead) {
|
|
294
|
+
span.setAttribute(GEN_AI.USAGE_CACHE_READ_INPUT_TOKENS, cacheRead);
|
|
295
|
+
}
|
|
296
|
+
if (cacheCreation) {
|
|
297
|
+
span.setAttribute(GEN_AI.USAGE_CACHE_CREATION_INPUT_TOKENS, cacheCreation);
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
if (response.model) {
|
|
301
|
+
span.setAttribute(GEN_AI.RESPONSE_MODEL, response.model);
|
|
302
|
+
}
|
|
303
|
+
if (response.stop_reason) {
|
|
304
|
+
span.setAttribute(GEN_AI.RESPONSE_FINISH_REASONS, [response.stop_reason]);
|
|
305
|
+
}
|
|
306
|
+
if (response.id) {
|
|
307
|
+
span.setAttribute(GEN_AI.RESPONSE_ID, response.id);
|
|
308
|
+
}
|
|
309
|
+
if (response.content) {
|
|
310
|
+
// Always runs — populates pending queue regardless of content-capture mode.
|
|
311
|
+
recordPendingToolCalls(response.content);
|
|
312
|
+
if (sdk.emitEvents && logger) {
|
|
313
|
+
emitAnthropicChoiceEvent(logger, response.content, response.stop_reason);
|
|
314
|
+
}
|
|
315
|
+
if (sdk.emitSpanContent) {
|
|
316
|
+
span.setAttribute(GEN_AI.OUTPUT_MESSAGES, toOutputMessages(response.content, response.stop_reason));
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
}
|
|
320
|
+
function recordPendingToolCalls(contentBlocks) {
|
|
321
|
+
const pairs = iterToolUses(contentBlocks);
|
|
322
|
+
if (pairs.length === 0)
|
|
323
|
+
return;
|
|
324
|
+
// Ensure the current store has a slot — initializes a transient dict if we're
|
|
325
|
+
// not inside a struct.agent() scope (matches Python behavior).
|
|
326
|
+
ensurePendingToolCallsSlot();
|
|
327
|
+
pushPendingToolCalls(pairs);
|
|
328
|
+
}
|
|
329
|
+
function propagateUserPromptToParent(messages) {
|
|
330
|
+
try {
|
|
331
|
+
const agentSpan = getAgentSpan();
|
|
332
|
+
if (!agentSpan)
|
|
333
|
+
return;
|
|
334
|
+
// The SDK span type doesn't expose `attributes` — we use a brand check on
|
|
335
|
+
// the SDK's ReadableSpan-like shape.
|
|
336
|
+
const agentAttrs = agentSpan
|
|
337
|
+
.attributes;
|
|
338
|
+
if (agentAttrs && agentAttrs[GEN_AI.INPUT_MESSAGES])
|
|
339
|
+
return;
|
|
340
|
+
const parts = lastUserMessageParts(messages);
|
|
341
|
+
if (!parts)
|
|
342
|
+
return;
|
|
343
|
+
agentSpan.setAttribute(GEN_AI.INPUT_MESSAGES, truncateAndSerialize([{ role: "user", parts }]));
|
|
344
|
+
}
|
|
345
|
+
catch {
|
|
346
|
+
/* never fail the application for telemetry */
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
function recordErrorOnSpan(span, err) {
|
|
350
|
+
const errorType = err instanceof Error ? err.constructor.name : typeof err;
|
|
351
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
352
|
+
span.setAttribute(ERROR_TYPE, errorType);
|
|
353
|
+
span.setStatus({ code: SpanStatusCode.ERROR, message });
|
|
354
|
+
if (err instanceof Error) {
|
|
355
|
+
span.recordException(err);
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
/** @internal */
|
|
359
|
+
export function _wrapCreateForTest(original) {
|
|
360
|
+
return wrapCreate(original);
|
|
361
|
+
}
|
|
362
|
+
/** @internal */
|
|
363
|
+
export function _wrapStreamForTest(original) {
|
|
364
|
+
return wrapStream(original);
|
|
365
|
+
}
|
|
366
|
+
/** @internal */
|
|
367
|
+
export function _setActivePatchCtxForTest(ctx) {
|
|
368
|
+
activePatchCtx.value = ctx;
|
|
369
|
+
}
|
|
370
|
+
//# sourceMappingURL=anthropic.js.map
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import type { StructSDK } from "../core.js";
|
|
2
|
+
export declare const patchedIntegrations: Set<string>;
|
|
3
|
+
export declare function resetPatchedIntegrations(): void;
|
|
4
|
+
export declare function autoInstrument(sdk: StructSDK): Promise<void>;
|
|
5
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
export const patchedIntegrations = new Set();
|
|
2
|
+
export function resetPatchedIntegrations() {
|
|
3
|
+
patchedIntegrations.clear();
|
|
4
|
+
}
|
|
5
|
+
const INTEGRATIONS = [
|
|
6
|
+
{
|
|
7
|
+
name: "anthropic",
|
|
8
|
+
probe: () => import("@anthropic-ai/sdk"),
|
|
9
|
+
apply: async (sdk) => {
|
|
10
|
+
const mod = await import("./anthropic.js");
|
|
11
|
+
await mod.patch(sdk);
|
|
12
|
+
},
|
|
13
|
+
},
|
|
14
|
+
{
|
|
15
|
+
name: "langchain",
|
|
16
|
+
probe: () => import("@langchain/core/language_models/chat_models"),
|
|
17
|
+
apply: async (sdk) => {
|
|
18
|
+
const mod = await import("./langchain.js");
|
|
19
|
+
await mod.patch(sdk);
|
|
20
|
+
},
|
|
21
|
+
},
|
|
22
|
+
];
|
|
23
|
+
export async function autoInstrument(sdk) {
|
|
24
|
+
for (const integration of INTEGRATIONS) {
|
|
25
|
+
if (patchedIntegrations.has(integration.name))
|
|
26
|
+
continue;
|
|
27
|
+
try {
|
|
28
|
+
await integration.probe();
|
|
29
|
+
}
|
|
30
|
+
catch {
|
|
31
|
+
continue;
|
|
32
|
+
}
|
|
33
|
+
try {
|
|
34
|
+
await integration.apply(sdk);
|
|
35
|
+
patchedIntegrations.add(integration.name);
|
|
36
|
+
}
|
|
37
|
+
catch (err) {
|
|
38
|
+
sdk.getInternalLogger().debug(`Failed to instrument ${integration.name}`, err);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
//# sourceMappingURL=index.js.map
|