From 6028420be12f9e38bbb6baa24b2aed0c12459035 Mon Sep 17 00:00:00 2001 From: Nithish-KV Date: Thu, 2 Jul 2026 21:58:58 +0530 Subject: [PATCH 1/5] [NET-1248] feat: Add support for capturing spans from anthropic tool runner (#96) --- package-lock.json | 4 +- package.json | 2 +- src/config.ts | 42 +- src/decorators.ts | 150 +-- src/index.ts | 19 +- src/instrumentation/anthropic/index.ts | 399 +++--- src/instrumentation/anthropic/types.ts | 16 + src/instrumentation/anthropic/utils.ts | 197 ++- src/instrumentation/anthropic/wrappers.ts | 1184 +++++++++-------- src/instrumentation/index.ts | 13 +- src/instrumentation/span-attributes.ts | 5 + src/instrumentation/utils.ts | 124 +- src/logger.ts | 4 + .../attribute-size-limit-processor.ts | 75 ++ src/processors/index.ts | 1 + src/processors/session-span-processor.ts | 10 + src/session-manager.ts | 30 +- src/utils/response-handler.ts | 234 ++++ src/utils/serialization.ts | 81 ++ src/version.ts | 1 + 20 files changed, 1642 insertions(+), 949 deletions(-) create mode 100644 src/instrumentation/anthropic/types.ts create mode 100644 src/processors/attribute-size-limit-processor.ts create mode 100644 src/utils/response-handler.ts create mode 100644 src/utils/serialization.ts create mode 100644 src/version.ts diff --git a/package-lock.json b/package-lock.json index d3f4977..aa7c856 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "netra-sdk", - "version": "1.3.0", + "version": "1.4.0-dev", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "netra-sdk", - "version": "1.3.0", + "version": "1.4.0-dev", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", diff --git a/package.json b/package.json index fd30832..4650bdb 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "netra-sdk", - "version": "1.3.0", + "version": "1.4.0-dev", "description": "A comprehensive TypeScript/JavaScript SDK for AI application observability built on top of OpenTelemetry and Traceloop", "type": "module", "main": "./dist/index.cjs", diff --git a/src/config.ts b/src/config.ts index 01095f4..43d0d13 100644 --- a/src/config.ts +++ b/src/config.ts @@ -3,6 +3,7 @@ */ import { Logger } from "./logger"; +import { SDK_VERSION } from "./version"; export interface NetraConfig { appName?: string; @@ -101,7 +102,7 @@ export const DEFAULT_INSTRUMENTS: Set = new Set([ export class Config { static readonly SDK_NAME = "netra"; static readonly LIBRARY_NAME = "netra"; - static readonly LIBRARY_VERSION = "1.0.0"; + static readonly LIBRARY_VERSION = SDK_VERSION; static readonly TRIAL_BLOCK_DURATION_SECONDS = 900; // 15 minutes static readonly ATTRIBUTE_MAX_LEN = parseInt( process.env.NETRA_ATTRIBUTE_MAX_LEN || "50000", @@ -109,6 +110,9 @@ export class Config { static readonly CONVERSATION_MAX_LEN = parseInt( process.env.NETRA_CONVERSATION_CONTENT_MAX_LEN || "50000", ); + static readonly SPAN_ATTRIBUTE_MAX_SIZE = parseInt( + process.env.NETRA_SPAN_ATTRIBUTE_MAX_SIZE || "30000", + ); appName: string; otlpEndpoint?: string; @@ -324,5 +328,41 @@ export class Config { .join(","); process.env.TRACELOOP_HEADERS = headerStr; } + + // Set OTEL_RESOURCE_ATTRIBUTES so the TracerProvider Resource carries + // service.name and deployment.environment attributes. + this._setResourceAttributesEnv(); + } + + private _setResourceAttributesEnv(): void { + // Start with Netra defaults (lowest priority) + const attrs: Record = { + "deployment.environment": this.environment, + "service.name": this.appName, + }; + + // Config-level resourceAttributes override defaults + for (const [k, v] of Object.entries(this.resourceAttributes)) { + attrs[k] = String(v); + } + + // Pre-existing OTEL_RESOURCE_ATTRIBUTES win (highest priority) + const existing = process.env.OTEL_RESOURCE_ATTRIBUTES; + if (existing) { + for (const pair of existing.split(",")) { + const eqIdx = pair.indexOf("="); + if (eqIdx <= 0) continue; + const key = decodeURIComponent(pair.slice(0, eqIdx).trim()); + if (key) { + attrs[key] = decodeURIComponent(pair.slice(eqIdx + 1).trim()); + } + } + } + + const encodeAttrValue = (s: string) => encodeURIComponent(s); + + process.env.OTEL_RESOURCE_ATTRIBUTES = Object.entries(attrs) + .map(([k, v]) => `${encodeAttrValue(k)}=${encodeAttrValue(v)}`) + .join(","); } } diff --git a/src/decorators.ts b/src/decorators.ts index b0010e3..903ce2f 100644 --- a/src/decorators.ts +++ b/src/decorators.ts @@ -2,11 +2,13 @@ * Decorators for easy instrumentation */ -import { trace, Span, SpanStatusCode } from "@opentelemetry/api"; +import { context, trace, Span, SpanStatusCode } from "@opentelemetry/api"; import { Config } from "./config"; import { Logger } from "./logger"; import { SessionManager } from "./session-manager"; import { SpanType, DecoratorOptions } from "./types"; +import { wrapResponse } from "./utils/response-handler"; +import { safeStringify, serializeValue } from "./utils/serialization"; type AnyFunction = (...args: any[]) => any; type AsyncFunction = (...args: any[]) => Promise; @@ -19,40 +21,6 @@ type MethodDecoratorFn = ( ) => void; type UnifiedDecorator = ClassDecoratorFn & MethodDecoratorFn; -/** - * Circular-reference-safe JSON.stringify. Non-serializable values - * (functions, symbols, cycles, complex class instances) become - * descriptive placeholders instead of throwing. - */ -function safeStringify(value: any, maxLen = 1000): string { - const seen = new WeakSet(); - try { - return JSON.stringify(value, (_key, val) => { - if (typeof val === "function") return `[Function: ${val.name || "anonymous"}]`; - if (typeof val === "symbol") return val.toString(); - if (typeof val === "bigint") return val.toString(); - if (val !== null && typeof val === "object") { - if (seen.has(val)) return "[Circular]"; - seen.add(val); - const name = val.constructor?.name; - if (name && name !== "Object" && name !== "Array" && Object.keys(val).length > 20) { - return `[${name}]`; - } - } - return val; - }).substring(0, maxLen); - } catch { - return value?.constructor?.name ? `[${value.constructor.name}]` : String(typeof value); - } -} - -function serializeValue(value: any): string { - if (value === null || value === undefined) return String(value); - const t = typeof value; - if (t === "string" || t === "number" || t === "boolean") return String(value); - return safeStringify(value); -} - /** * Returns true if the span already has a non-empty `output` attribute. * Checks both the public `attributes` property and the internal `_attributes` @@ -70,14 +38,10 @@ function spanHasOutput(span: Span): boolean { return false; } -function addInputAttributes( - span: Span, - args: any[], - entityType: string, -): void { +function addInputAttributes(span: Span, args: any[], entityType: string): void { span.setAttribute(`${Config.LIBRARY_NAME}.entity.type`, entityType); if (args.length > 0) { - span.setAttribute("input", safeStringify(args)); + span.setAttribute("input", safeStringify(args, Config.ATTRIBUTE_MAX_LEN)); } } @@ -85,7 +49,7 @@ function addOutputAttributes(span: Span, result: any): void { // Skip if the user already set output explicitly inside the decorated function if (spanHasOutput(span)) return; try { - span.setAttribute("output", serializeValue(result)); + span.setAttribute("output", serializeValue(result, Config.ATTRIBUTE_MAX_LEN)); } catch (e) { span.setAttribute("output_error", String(e)); } @@ -119,14 +83,13 @@ function createFunctionWrapper( SessionManager.registerSpan(spanName, span); }; - const handleError = (span: Span, e: any) => { + const recordError = (span: Span, e: any) => { span.setAttribute(`${Config.LIBRARY_NAME}.entity.error`, String(e)); span.setStatus({ code: SpanStatusCode.ERROR, message: e instanceof Error ? e.message : String(e), }); span.recordException(e); - throw e; }; const cleanup = (span: Span) => { @@ -135,65 +98,52 @@ function createFunctionWrapper( SessionManager.popEntity(entityType); }; - if (isAsync) { - const wrapper = async function (this: any, ...args: any[]) { - SessionManager.pushEntity(entityType, spanName); - const tracer = trace.getTracer(moduleName); - return tracer.startActiveSpan(spanName, async (span) => { - try { - initSpan(span); - addInputAttributes(span, args, entityType); - const result = await (func as AsyncFunction).call(this, ...args); - addOutputAttributes(span, result); - return result; - } catch (e: any) { - handleError(span, e); - } finally { - cleanup(span); - } - }); - }; - return wrapper as T; - } else { - const wrapper = function (this: any, ...args: any[]) { - SessionManager.pushEntity(entityType, spanName); - const tracer = trace.getTracer(moduleName); - return tracer.startActiveSpan(spanName, (span) => { - // Track whether the function returned a promise so the finally block - // can skip its cleanup — the promise chain owns span lifecycle in that case. - let returnedPromise = false; - try { - initSpan(span); - addInputAttributes(span, args, entityType); - const result = (func as AnyFunction).call(this, ...args); - - // Detect promise-returning non-async functions (e.g. `function foo() { return fetch(...) }`) - // Without this check, addOutputAttributes would capture the raw Promise object and - // cleanup() would end the span before the async work completes. - if (result != null && typeof (result as any).then === "function") { - returnedPromise = true; - return (result as Promise) - .then((resolved: any) => { - addOutputAttributes(span, resolved); - return resolved; - }) - .catch((e: any) => handleError(span, e)) - .finally(() => cleanup(span)); + const wrapperFn = isAsync + ? async function (this: any, ...args: any[]) { + SessionManager.pushEntity(entityType, spanName); + const tracer = trace.getTracer(moduleName); + return tracer.startActiveSpan(spanName, async (span) => { + try { + initSpan(span); + addInputAttributes(span, args, entityType); + const result = await (func as AsyncFunction).call(this, ...args); + const spanCtx = trace.setSpan(context.active(), span); + return wrapResponse(result, { + withContext: (fn) => context.with(spanCtx, fn), + onError: (e) => recordError(span, e), + onSuccess: (value) => addOutputAttributes(span, value), + finalize: () => cleanup(span), + }); + } catch (e: any) { + recordError(span, e); + cleanup(span); + throw e; } - - addOutputAttributes(span, result); - return result; - } catch (e: any) { - handleError(span, e); - } finally { - if (!returnedPromise) { + }); + } + : function (this: any, ...args: any[]) { + SessionManager.pushEntity(entityType, spanName); + const tracer = trace.getTracer(moduleName); + return tracer.startActiveSpan(spanName, (span) => { + try { + initSpan(span); + addInputAttributes(span, args, entityType); + const result = (func as AnyFunction).call(this, ...args); + const spanCtx = trace.setSpan(context.active(), span); + return wrapResponse(result, { + withContext: (fn) => context.with(spanCtx, fn), + onError: (e) => recordError(span, e), + onSuccess: (value) => addOutputAttributes(span, value), + finalize: () => cleanup(span), + }); + } catch (e: any) { + recordError(span, e); cleanup(span); + throw e; } - } - }); - }; - return wrapper as T; - } + }); + }; + return wrapperFn as T; } const SKIP_STATIC_PROPS = new Set([ diff --git a/src/index.ts b/src/index.ts index 90bade6..1cd80b1 100644 --- a/src/index.ts +++ b/src/index.ts @@ -16,6 +16,7 @@ import { Simulation } from "./simulation"; import { SpanWrapper } from "./span-wrapper"; import { Tracer } from "./tracer"; import { SpanType, SpanCallback, SpanOptions, SpanAttributes } from "./types"; +import { wrapResponse } from "./utils/response-handler"; export { Config, @@ -25,6 +26,7 @@ export { } from "./config"; export { agent, span, task, workflow } from "./decorators"; export { + AttributeSizeLimitProcessor, InstrumentationSpanProcessor, ScrubbingSpanProcessor, SessionSpanProcessor, @@ -530,17 +532,12 @@ export class Netra { throw e; } - if (result instanceof Promise) { - return (result as Promise) - .catch((e) => { - spanWrapper.setError(e instanceof Error ? e.message : String(e)); - throw e; - }) - .finally(() => spanWrapper.end()) as T; - } - - spanWrapper.end(); - return result; + return wrapResponse(result, { + withContext: (fn) => spanWrapper.withActive(fn), + onError: (e) => + spanWrapper.setError(e instanceof Error ? e.message : String(e)), + finalize: () => spanWrapper.end(), + }) as T; }); } diff --git a/src/instrumentation/anthropic/index.ts b/src/instrumentation/anthropic/index.ts index 962335f..5dcb927 100644 --- a/src/instrumentation/anthropic/index.ts +++ b/src/instrumentation/anthropic/index.ts @@ -1,34 +1,38 @@ import { createRequire } from "module"; -import { context, SpanKind, trace, Tracer, TracerProvider } from "@opentelemetry/api"; +import { trace, Tracer, TracerProvider } from "@opentelemetry/api"; +import shimmer from "shimmer"; import { Logger } from "../../logger"; -import { setRequestAttributes } from "./utils"; +import { SPAN_NAMES, InstrumentorOptions } from "./types"; import { __version__ } from "./version"; -import { batchesWrapper, betaWrapper, chatWrapper, MessageStreamWrapper } from "./wrappers"; +import { + batchesWrapper, + betaStreamWrapper, + betaWrapper, + betaToolRunnerWrapper, + chatStreamWrapper, + chatWrapper, +} from "./wrappers"; const INSTRUMENTATION_NAME = "netra.instrumentation.anthropic"; const INSTRUMENTS = ["anthropic >= 0.71.2"]; -const originalMethods: Map = new Map(); let isInstrumented = false; let anthropicClasses: any[] = []; - -export interface InstrumentorOptions { - tracerProvider?: TracerProvider; -} - /** * Resolve the Anthropic module from the application's context. - * Tries ESM dynamic import first, then falls back to CJS require so the - * instrumentor works in both ESM and CommonJS projects. + * Tries ESM dynamic import first, then falls back to CJS require. + * Returns cached classes on subsequent calls. */ -async function resolveAnthropicAsync(): Promise { +async function resolveAnthropic(): Promise { if (anthropicClasses.length > 0) return anthropicClasses; try { // @ts-ignore - @anthropic-ai/sdk is an optional peer dependency const anthropicModule = await import("@anthropic-ai/sdk"); - anthropicClasses.push(anthropicModule.Anthropic || anthropicModule.default || anthropicModule); + anthropicClasses.push( + anthropicModule.Anthropic || anthropicModule.default || anthropicModule, + ); } catch { Logger.warn("Failed to resolve Anthropic ESM module"); } @@ -47,70 +51,64 @@ async function resolveAnthropicAsync(): Promise { return anthropicClasses; } -function resolveAnthropic(): any[] { - return anthropicClasses; -} +export class NetraAnthropicInstrumentor { + private tracer: Tracer | null = null; + private tracerProvider?: TracerProvider; + constructor() {} -export class NetraAnthropicInstrumentor { - private tracer: Tracer | null = null; - private tracerProvider?: TracerProvider; + instrumentationDependencies(): string[] { + return INSTRUMENTS; + } + + async instrument( + options: InstrumentorOptions = {}, + ): Promise { + if (isInstrumented) { + Logger.warn("Anthropic is already instrumented"); + return this; + } + + const classes = await resolveAnthropic(); + if (classes.length === 0) return this; - constructor() {} - instrumentationDependencies(): string[] { - return INSTRUMENTS; + try { + this.tracerProvider = options.tracerProvider; + if (this.tracerProvider) { + this.tracer = this.tracerProvider.getTracer( + INSTRUMENTATION_NAME, + __version__, + ); + } else { + this.tracer = trace.getTracer(INSTRUMENTATION_NAME, __version__); } + } catch (error) { + Logger.error(`Failed to initialize tracer: ${error}`); + return this; + } - async instrumentAsync(options: InstrumentorOptions = {}): Promise { - if (isInstrumented) { - Logger.warn("Anthropic is already instrumented"); - return this; - } - - const classes = await resolveAnthropicAsync(); - if (classes.length === 0) { - return this; - } - - try { - this.tracerProvider = options.tracerProvider; - if (this.tracerProvider) { - this.tracer = this.tracerProvider.getTracer( - INSTRUMENTATION_NAME, - __version__ - ); - } else { - this.tracer = trace.getTracer(INSTRUMENTATION_NAME, __version__); - } - } catch (error) { - Logger.error(`Failed to initialize tracer: ${error}`); - return this; - } - - classes.forEach((AnthropicSDK, index) => { - this._instrumentMessages(AnthropicSDK, index); - this._instrumentBetaMessages(AnthropicSDK, index); - this._instrumentBatchMessages(AnthropicSDK, index); + classes.forEach((AnthropicSDK) => { + this._instrumentMessages(AnthropicSDK); + this._instrumentBetaMessages(AnthropicSDK); + this._instrumentBatchMessages(AnthropicSDK); }); isInstrumented = true; return this; } - uninstrument(): void{ - if (!isInstrumented) { - Logger.warn("Anthropic is not instrumented"); - return; - } + uninstrument(): void { + if (!isInstrumented) { + Logger.warn("Anthropic is not instrumented"); + return; + } - const classes = resolveAnthropic(); - classes.forEach((AnthropicSDK, index) => { - this._uninstrumentMessages(AnthropicSDK, index); - this._uninstrumentBetaMessages(AnthropicSDK, index); - this._uninstrumentBatchMessages(AnthropicSDK, index); + anthropicClasses.forEach((AnthropicSDK) => { + this._uninstrumentMessages(AnthropicSDK); + this._uninstrumentBetaMessages(AnthropicSDK); + this._uninstrumentBatchMessages(AnthropicSDK); }); - originalMethods.clear(); anthropicClasses = []; isInstrumented = false; } @@ -119,209 +117,142 @@ export class NetraAnthropicInstrumentor { return isInstrumented; } -private _instrumentMessages(AnthropicSDK: any, index: number): void { - if (!this.tracer) { - Logger.warn("Anthropic instrumentation: No tracer available"); - return; - } - try { - const MessagesClass = AnthropicSDK.Messages; - if (!MessagesClass) { - Logger.error( - "Anthropic instrumentation: Could not find Anthropic Messages class to instrument", - ); + private _instrumentMessages(AnthropicSDK: any): void { + if (!this.tracer) { + Logger.warn("Anthropic instrumentation: No tracer available"); return; } + try { + const MessagesClass = AnthropicSDK.Messages; + if (!MessagesClass?.prototype) { + Logger.error( + "Anthropic instrumentation: Could not find Messages class", + ); + return; + } - if (MessagesClass?.prototype?.stream) { - const originalStream = MessagesClass.prototype.stream as Function; - originalMethods.set(`messages.stream-${index}`, originalStream); - const tracer = this.tracer; - MessagesClass.prototype.stream = function ( - this: unknown, - ...args: unknown[] - ): unknown { - const original = originalStream.bind(this); - const kwargs = (args[0] || {}) as Record; - - const currentContext = context.active(); - const span = tracer.startSpan("anthropic" + ".stream", { - kind: SpanKind.CLIENT, - attributes: { - "llm.request.type": "chat", - "llm.streaming": true, - "llm.operation": "stream" - }, - }, currentContext); - - const spanContext = trace.setSpan(currentContext, span); - - setRequestAttributes(span, kwargs, "chat"); - const startTime = Date.now(); - - const instrumentedCreate = (this as any).create; - const originalCreate = originalMethods.get(`messages.create-${index}`); - if (originalCreate) { - (this as any).create = originalCreate; - } - - try { - const messageStream = context.with(spanContext, () => original(...args)); - return new MessageStreamWrapper(span, messageStream, startTime, kwargs, spanContext); - } finally { - if (originalCreate) { - (this as any).create = instrumentedCreate; - } - } - } as typeof MessagesClass.prototype.stream; - } + const originalCreate = MessagesClass.prototype.create; - if (MessagesClass?.prototype?.create) { - const originalCreate = MessagesClass.prototype.create as Function; - originalMethods.set(`messages.create-${index}`, originalCreate); - const tracer = this.tracer; - const wrapper = chatWrapper(tracer); - - MessagesClass.prototype.create = function ( - this: unknown, - ...args: unknown[] - ): unknown { - const original = originalCreate.bind(this); - const kwargs = (args[0] || {}) as Record; - - return wrapper( - (...a: unknown[]) => original(...a), - this, - args, - kwargs, + if (typeof MessagesClass.prototype.create === "function") { + shimmer.wrap( + MessagesClass.prototype, + "create", + chatWrapper(this.tracer), ); - } as typeof MessagesClass.prototype.create; + } + + if (typeof MessagesClass.prototype.stream === "function") { + shimmer.wrap( + MessagesClass.prototype, + "stream", + chatStreamWrapper(this.tracer, originalCreate), + ); + } + } catch (error) { + Logger.error(`Failed to instrument messages: ${error}`); } - } catch (error) { - Logger.error(`Failed to instrument messages: ${error}`); } -} -private _instrumentBetaMessages(AnthropicSDK: any, index: number): void { - if (!this.tracer) { - Logger.warn("Anthropic instrumentation: No tracer available"); - return; - } - try { - const BetaMessagesClass = AnthropicSDK.Beta?.Messages; - if (!BetaMessagesClass) { - Logger.error( - "Anthropic instrumentation: Could not find Anthropic Beta Messages class to instrument", - ); + private _instrumentBetaMessages(AnthropicSDK: any): void { + if (!this.tracer) { + Logger.warn("Anthropic instrumentation: No tracer available"); return; } + try { + const BetaMessagesClass = AnthropicSDK.Beta?.Messages; + if (!BetaMessagesClass?.prototype) { + Logger.error( + "Anthropic instrumentation: Could not find Beta Messages class", + ); + return; + } + + const originalCreate = BetaMessagesClass.prototype.create; + + if (typeof BetaMessagesClass.prototype.create === "function") { + shimmer.wrap( + BetaMessagesClass.prototype, + "create", + betaWrapper(this.tracer), + ); + } + + if (typeof BetaMessagesClass.prototype.stream === "function") { + shimmer.wrap( + BetaMessagesClass.prototype, + "stream", + betaStreamWrapper(this.tracer, originalCreate), + ); + } - if (BetaMessagesClass?.prototype?.create) { - const originalCreate = BetaMessagesClass.prototype.create as Function; - originalMethods.set(`beta.messages.create-${index}`, originalCreate); - const tracer = this.tracer; - const wrapper = betaWrapper(tracer); - - BetaMessagesClass.prototype.create = function ( - this: unknown, - ...args: unknown[] - ): unknown { - const original = originalCreate.bind(this); - const kwargs = (args[0] || {}) as Record; - - return wrapper( - (...a: unknown[]) => original(...a), - this, - args, - kwargs, + if (typeof BetaMessagesClass.prototype.toolRunner === "function") { + shimmer.wrap( + BetaMessagesClass.prototype, + "toolRunner", + betaToolRunnerWrapper(this.tracer), ); - } as typeof BetaMessagesClass.prototype.create; + } + } catch (error) { + Logger.error(`Failed to instrument beta: ${error}`); } - } catch (error) { - Logger.error(`Failed to instrument beta: ${error}`); } -} -private _instrumentBatchMessages(AnthropicSDK: any, index: number):void { - if (!this.tracer) { - Logger.warn("Anthropic instrumentation: No tracer available"); - return; - } - try { - const BatchMessageClass = AnthropicSDK.Messages?.Batches; - if (!BatchMessageClass) { - Logger.error( - "Anthropic instrumentation: Could not find Anthropic Batches class to instrument", - ); + private _instrumentBatchMessages(AnthropicSDK: any): void { + if (!this.tracer) { + Logger.warn("Anthropic instrumentation: No tracer available"); return; } + try { + const BatchMessageClass = AnthropicSDK.Messages?.Batches; + if (!BatchMessageClass?.prototype) { + Logger.error("Anthropic instrumentation: Could not find Batches class"); + return; + } - if (BatchMessageClass?.prototype?.create) { - const originalCreate = BatchMessageClass.prototype.create as Function; - originalMethods.set(`batch.messages.create-${index}`, originalCreate); - const tracer = this.tracer; - const wrapper = batchesWrapper(tracer); - - BatchMessageClass.prototype.create = function ( - this: unknown, - ...args: unknown[] - ): unknown { - const original = originalCreate.bind(this); - const kwargs = (args[0] || {}) as Record; - - return wrapper( - (...a: unknown[]) => original(...a), - this, - args, - kwargs, + if (typeof BatchMessageClass.prototype.create === "function") { + shimmer.wrap( + BatchMessageClass.prototype, + "create", + batchesWrapper(this.tracer), ); - } as typeof BatchMessageClass.prototype.create; + } + } catch (error) { + Logger.error(`Failed to instrument batches: ${error}`); } - } catch (error) { - Logger.error(`Failed to instrument batches: ${error}`); } -} - private _uninstrumentMessages(AnthropicSDK: any, index: number): void { - try { - const MessagesClass = AnthropicSDK.Messages; - const originalCreate = originalMethods.get(`messages.create-${index}`); - if (originalCreate && MessagesClass?.prototype) { - MessagesClass.prototype.create = - originalCreate as typeof MessagesClass.prototype.create; - } + private _uninstrumentMessages(AnthropicSDK: any): void { + try { + const proto = AnthropicSDK.Messages?.prototype; + if (!proto) return; - const originalStream = originalMethods.get(`messages.stream-${index}`); - if (originalStream && MessagesClass?.prototype) { - MessagesClass.prototype.stream = - originalStream as typeof MessagesClass.prototype.stream; - } + if (typeof proto.create === "function") shimmer.unwrap(proto, "create"); + if (typeof proto.stream === "function") shimmer.unwrap(proto, "stream"); } catch (error) { Logger.error(`Failed to uninstrument messages: ${error}`); } } - private _uninstrumentBetaMessages(AnthropicSDK: any, index: number): void { + + private _uninstrumentBetaMessages(AnthropicSDK: any): void { try { - const BetaMessagesClass = AnthropicSDK.Beta?.Messages; + const proto = AnthropicSDK.Beta?.Messages?.prototype; + if (!proto) return; - const originalCreate = originalMethods.get(`beta.messages.create-${index}`); - if (originalCreate && BetaMessagesClass?.prototype) { - BetaMessagesClass.prototype.create = - originalCreate as typeof BetaMessagesClass.prototype.create; - } + if (typeof proto.create === "function") shimmer.unwrap(proto, "create"); + if (typeof proto.stream === "function") shimmer.unwrap(proto, "stream"); + if (typeof proto.toolRunner === "function") + shimmer.unwrap(proto, "toolRunner"); } catch (error) { Logger.error(`Failed to uninstrument beta: ${error}`); } } - private _uninstrumentBatchMessages(AnthropicSDK: any, index: number): void { + + private _uninstrumentBatchMessages(AnthropicSDK: any): void { try { - const BatchMessagesClass = AnthropicSDK.Messages?.Batches; + const proto = AnthropicSDK.Messages?.Batches?.prototype; + if (!proto) return; - const originalCreate = originalMethods.get(`batch.messages.create-${index}`); - if (originalCreate && BatchMessagesClass?.prototype) { - BatchMessagesClass.prototype.create = - originalCreate as typeof BatchMessagesClass.prototype.create; - } + if (typeof proto.create === "function") shimmer.unwrap(proto, "create"); } catch (error) { Logger.error(`Failed to uninstrument batches: ${error}`); } @@ -329,9 +260,3 @@ private _instrumentBatchMessages(AnthropicSDK: any, index: number):void { } export const anthropicInstrumentor = new NetraAnthropicInstrumentor(); - -export { AsyncStreamingWrapper, chatWrapper } from "./wrappers"; - -export { setRequestAttributes, setResponseAttributes } from "./utils"; - -export { __version__ } from "./version"; diff --git a/src/instrumentation/anthropic/types.ts b/src/instrumentation/anthropic/types.ts new file mode 100644 index 0000000..fb3b2f2 --- /dev/null +++ b/src/instrumentation/anthropic/types.ts @@ -0,0 +1,16 @@ +import { TracerProvider } from "@opentelemetry/api"; + +export type AnthropicRequestType = "chat" | "beta" | "batches"; + +export const SPAN_NAMES = { + CHAT: "anthropic.chat", + STREAM: "anthropic.stream", + BATCHES: "anthropic.batches", + BETA: "anthropic.beta", + BETA_STREAM: "anthropic.beta.stream", + BETA_TOOL_RUNNER: "anthropic.beta.tool.runner", +} as const; + +export interface InstrumentorOptions { + tracerProvider?: TracerProvider; +} diff --git a/src/instrumentation/anthropic/utils.ts b/src/instrumentation/anthropic/utils.ts index 1136840..b378226 100644 --- a/src/instrumentation/anthropic/utils.ts +++ b/src/instrumentation/anthropic/utils.ts @@ -1,32 +1,201 @@ -import { Span } from "@opentelemetry/api"; +import { Span, SpanStatusCode } from "@opentelemetry/api"; import { Logger } from "../../logger"; import { setRequestAttributes as setBaseRequestAttributes, setResponseAttributes as setBaseResponseAttributes, } from "../utils"; +/** + * Accumulate a single Anthropic SSE chunk into `completeResponse`. + * Safe against malformed events — all field access is guarded. + */ +export function processStreamChunk( + completeResponse: Record, + chunk: any, + span: Span, +): void { + try { + switch (chunk.type) { + case "message_start": { + if (chunk.message?.model) { + completeResponse.model = chunk.message.model; + } + if (chunk.message?.usage) { + completeResponse.usage = chunk.message.usage; + } + break; + } + + case "content_block_start": { + if (!completeResponse.content) { + completeResponse.content = []; + } + const block = chunk.content_block; + if (!block) break; + if (block.type === "tool_use") { + completeResponse.content.push({ + type: "tool_use", + id: block.id, + name: block.name, + input: "", + }); + } else { + completeResponse.content.push({ + type: block.type, + text: "", + }); + } + break; + } + + case "content_block_delta": { + if ( + !completeResponse.content || + completeResponse.content.length === 0 + ) { + completeResponse.content = [{ type: "text", text: "" }]; + } + const targetIndex = + chunk.index ?? completeResponse.content.length - 1; + const targetBlock = completeResponse.content[targetIndex]; + if (!targetBlock) break; + + if ( + chunk.delta?.type === "input_json_delta" && + targetBlock.type === "tool_use" + ) { + targetBlock.input += chunk.delta.partial_json ?? ""; + } else if (chunk.delta?.text) { + targetBlock.text += chunk.delta.text; + } + break; + } + + case "content_block_stop": { + const blocks = completeResponse.content; + if (blocks && blocks.length > 0) { + const finishedBlock = blocks[blocks.length - 1]; + if ( + finishedBlock?.type === "tool_use" && + typeof finishedBlock.input === "string" + ) { + try { + finishedBlock.input = JSON.parse(finishedBlock.input); + } catch { + Logger.warn( + "netra.instrumentation.anthropic: Failed to parse tool use input", + ); + } + } + } + break; + } + + case "message_delta": { + if (chunk.delta?.stop_reason) { + completeResponse.stop_reason = chunk.delta.stop_reason; + } + const usageData = chunk.usage ?? chunk.delta?.usage; + if (usageData) { + completeResponse.usage = { + ...(completeResponse.usage ?? {}), + ...usageData, + }; + } + break; + } + + case "message_stop": { + if (chunk.usage) { + completeResponse.usage = { + ...(completeResponse.usage ?? {}), + ...chunk.usage, + }; + } + break; + } + } + + if (Logger.isDebugMode()) { + span.addEvent("llm.content.completion.chunk", { + "chunk.type": chunk.type, + }); + } + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: processStreamChunk error", + e, + ); + } +} + +/** + * Close out a streaming span: set response attributes, record duration, and end. + */ +export function finalizeStreamSpan( + span: Span, + completeResponse: Record, + startTime: number, + code: SpanStatusCode, +): void { + try { + const endTime = Date.now(); + + setResponseAttributes(span, { + model: completeResponse.model, + content: completeResponse.content, + usage: completeResponse.usage, + stop_reason: completeResponse.stop_reason, + }); + + span.setAttribute("llm.response.duration", (endTime - startTime) / 1000); + span.setStatus({ code }); + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: finalizeStreamSpan error", + e, + ); + } finally { + span.end(); + } +} + export function setRequestAttributes( span: Span, kwargs: Record, - requestType: string + requestType: string, ): void { - if (!span.isRecording()) { - Logger.log("Span is not recording"); - return; + try { + if (!span.isRecording()) { + Logger.log("Span is not recording"); + return; + } + setBaseRequestAttributes(span, kwargs, requestType, "anthropic"); + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: setRequestAttributes error", + e, + ); } - setBaseRequestAttributes(span, kwargs, requestType, "anthropic"); } export function setResponseAttributes( span: Span, - response: Record + response: Record, ): void { - if (!span.isRecording()) { - Logger.log("Span is not recording"); - return; - } - if(response?.type === 'message_batch'){ - span.setAttribute("status", response?.processing_status as string); + try { + if (!span.isRecording()) { + Logger.log("Span is not recording"); + return; + } + if (response?.type === "message_batch") { + span.setAttribute("status", response?.processing_status as string); + } + setBaseResponseAttributes(span, response); + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: setResponseAttributes error", + e, + ); } - setBaseResponseAttributes(span, response); } diff --git a/src/instrumentation/anthropic/wrappers.ts b/src/instrumentation/anthropic/wrappers.ts index d26559d..382e210 100644 --- a/src/instrumentation/anthropic/wrappers.ts +++ b/src/instrumentation/anthropic/wrappers.ts @@ -1,323 +1,341 @@ -import { context, Span, SpanKind, SpanStatusCode, trace, Tracer } from "@opentelemetry/api"; +import { + context, + Context, + Span, + SpanKind, + SpanStatusCode, + trace, + Tracer, +} from "@opentelemetry/api"; import { Logger } from "../../logger"; -import { defineHidden, isPromise, modelAsDict, shouldSuppressInstrumentation } from "../utils"; -import { setRequestAttributes, setResponseAttributes } from "./utils"; +import { wrapResponse } from "../../utils/response-handler"; +import { safeStringify } from "../../utils/serialization"; +import { SpanAttributes } from "../span-attributes"; +import { + defineHidden, + isTraceContentEnabled, + modelAsDict, + shouldSuppressInstrumentation, +} from "../utils"; +import { AnthropicRequestType, SPAN_NAMES } from "./types"; +import { + finalizeStreamSpan, + processStreamChunk, + setRequestAttributes, + setResponseAttributes, +} from "./utils"; -type AnthropicRequestType = "chat" | "beta" | "batches"; +const WRAPPER_OWN_PROPS = new Set([ + "span", + "messageStream", + "startTime", + "requestKwargs", + "completeResponse", + "finalizeSpanOnce", + "processEventData", + "finalizeSpanFromMessage", + "parentContext", + "spanFinalized", + "completionPending", + "listenerMap", +]); -const CHAT_SPAN_NAME = "anthropic.chat"; -const BETA_SPAN_NAME = "anthropic.beta"; -const BATCHES_SPAN_NAME = "anthropic.batches"; -const STREAM_ENABLED_REQUESTS: AnthropicRequestType[] = ["chat", "beta"]; +const EVENT_EMITTER_METHODS = new Set([ + "on", + "once", + "off", + "removeListener", + "addListener", + "emit", + "removeAllListeners", + "listeners", + "listenerCount", +]); -function anthropicWrapper( - tracer: Tracer, - spanName: string, - requestType: AnthropicRequestType -) { - return function wrapper any>( - wrapped: F, - instance: unknown, - args: Parameters, - kwargs: Record & { stream?: boolean } - ): unknown { - if (shouldSuppressInstrumentation()) { - const result = wrapped.call(instance, ...args); - return isPromise(result) ? result.then((value) => value) : result; - } - const currentContext = context.active(); - const isStreaming = args[0]?.stream === true; - - const activeSpan = trace.getSpan(context.active()); - Logger.debug(`Anthropic invoke (${requestType}). Active TraceId: ${activeSpan?.spanContext().traceId}, SpanId: ${activeSpan?.spanContext().spanId}`); - - if (isStreaming && STREAM_ENABLED_REQUESTS.includes(requestType)) { - const span = tracer.startSpan(spanName + ".create", { - kind: SpanKind.CLIENT, - attributes: { - "llm.request.type": requestType, - "llm.streaming": true - }, - }, - currentContext); +const LISTENER_REGISTRATION_METHODS = new Set(["on", "once", "addListener"]); +const LISTENER_REMOVAL_METHODS = new Set(["off", "removeListener"]); +const COMPLETION_METHODS = new Set(["finalMessage", "done", "finalText"]); - try { - setRequestAttributes(span, kwargs, requestType); - const startTime = Date.now(); +const TRACKED_STREAM_EVENTS = new Set([ + "message", + "contentBlock", + "text", + "finalMessage", +]); - // Call the original function and get the APIPromise - const spanContext = trace.setSpan(currentContext, span); - const response = context.with(spanContext, () => wrapped.call(instance, ...args)); +const MAX_TOOL_ATTR_LENGTH = 4096; - if (isPromise(response)) { - return (async () => { - try { - const stream = await response; - return new AsyncStreamingWrapper(span, stream, startTime, kwargs, spanContext); - } catch (error) { - Logger.error("netra.instrumentation.anthropic:", error); - span.setStatus({ - code: SpanStatusCode.ERROR, - message: error instanceof Error ? error.message : String(error), - }); - span.recordException(error as Error); - span.end(); - throw error; - } - })(); - } else { - return new AsyncStreamingWrapper(span, response, startTime, kwargs, spanContext); - } +/** + * Wrap each tool's `run()` method so every invocation produces a TOOL span. + * Preserves the tool's prototype chain — only `run` is replaced. + * User tool errors are recorded on the span and re-thrown. + */ +export function wrapRunnableTools( + tools: any[], + tracer: Tracer, + parentContext: Context, +): any[] { + return tools.map((tool) => { + if (typeof tool.run !== "function") return tool; + + const originalRun = tool.run; + const toolName = tool.name ?? "unknown_tool"; + + const wrappedRun = async function ( + this: any, + input: any, + runContext?: any, + ) { + const toolUseId = runContext?.toolUse?.id ?? runContext?.toolUseBlock?.id; + const traceContent = isTraceContentEnabled(); + const attrs: Record = { + "netra.span.type": "TOOL", + [SpanAttributes.LLM_REQUEST_TOOL_NAME]: toolName, + }; + if (toolUseId) attrs[SpanAttributes.LLM_REQUEST_TOOL_ID] = toolUseId; + if (traceContent) { + attrs.input = safeStringify(input, MAX_TOOL_ATTR_LENGTH); + } + const span = tracer.startSpan( + toolName, + { kind: SpanKind.INTERNAL, attributes: attrs }, + parentContext, + ); + + const spanCtx = trace.setSpan(parentContext, span); + try { + const result = await context.with(spanCtx, () => + originalRun.call(this, input, runContext), + ); + if (traceContent) { + span.setAttribute( + "output", + safeStringify(result, MAX_TOOL_ATTR_LENGTH), + ); + } + span.setStatus({ code: SpanStatusCode.OK }); + return result; } catch (error) { - Logger.error("netra.instrumentation.anthropic:", error); span.setStatus({ code: SpanStatusCode.ERROR, message: error instanceof Error ? error.message : String(error), }); span.recordException(error as Error); - span.end(); throw error; + } finally { + span.end(); } - } - // Non streaming - else { - return tracer.startActiveSpan( - spanName, - { - kind: SpanKind.CLIENT, - attributes: { "llm.request.type": requestType }, - }, - (span: Span) => { - try { - setRequestAttributes(span, kwargs, requestType); - const startTime = Date.now(); - const spanContext = trace.setSpan(currentContext, span); - const response = context.with(spanContext, () => wrapped.call(instance, ...args)); - if (isPromise(response)) { - // Create a new promise that handles instrumentation - const instrumentedPromise = (async () => { - try { - const value = await response; - const endTime = Date.now(); - const responseDict = modelAsDict(value); - setResponseAttributes(span, responseDict); - span.setAttribute( - "llm.response.duration", - (endTime - startTime) / 1000 - ); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return value; - } catch (error) { - Logger.error("netra.instrumentation.anthropic:", error); - span.setStatus({ - code: SpanStatusCode.ERROR, - message: - error instanceof Error ? error.message : String(error), - }); - span.recordException(error as Error); - span.end(); - throw error; - } - })(); - - // Use a Proxy to preserve all methods from the original APIPromise - // This includes withResponse(), asResponse(), etc. - return new Proxy(instrumentedPromise, { - get(target, prop, receiver) { - // Special handling for then/catch/finally - use our instrumented promise - if (prop === 'then' || prop === 'catch' || prop === 'finally') { - const value = Reflect.get(target, prop, receiver); - if (typeof value === 'function') { - return value.bind(target); - } - return value; - } - - // For all other properties, first check the original response object - // This ensures methods like withResponse() are available - const responseValue = (response as any)[prop]; - if (responseValue !== undefined) { - if (typeof responseValue === 'function') { - return responseValue.bind(response); - } - return responseValue; - } - - // Fall back to the instrumented promise - const value = Reflect.get(target, prop, receiver); - if (typeof value === 'function') { - return value.bind(target); - } - return value; - } - }); - } else { - const endTime = Date.now(); - const responseDict = modelAsDict(response); - setResponseAttributes(span, responseDict); - span.setAttribute( - "llm.response.duration", - (endTime - startTime) / 1000 - ); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return response; - } - } catch (error) { - Logger.error("netra.instrumentation.anthropic:", error); - span.setStatus({ - code: SpanStatusCode.ERROR, - message: error instanceof Error ? error.message : String(error), - }); - span.recordException(error as Error); - span.end(); - throw error; - } - } - ); - } - }; + }; + + const wrapped = Object.create( + Object.getPrototypeOf(tool), + Object.getOwnPropertyDescriptors(tool), + ); + wrapped.run = wrappedRun; + return wrapped; + }); } -export const chatWrapper = (tracer: Tracer) => - anthropicWrapper(tracer, CHAT_SPAN_NAME, "chat"); - -export const betaWrapper = (tracer: Tracer) => - anthropicWrapper(tracer, BETA_SPAN_NAME, "beta"); - -export const batchesWrapper = (tracer: Tracer) => - anthropicWrapper(tracer, BATCHES_SPAN_NAME, "batches"); - - -const WRAPPER_OWN_PROPS = new Set([ - 'span', 'messageStream', 'startTime', 'requestKwargs', 'completeResponse', - 'processChunk', 'finalizeSpan', 'processEventData', 'finalizeSpanFromMessage', -]); - -const EVENT_EMITTER_METHODS = new Set([ - 'on', 'once', 'off', 'removeListener', 'addListener', - 'emit', 'removeAllListeners', 'listeners', 'listenerCount', -]); - -const LISTENER_REGISTRATION_METHODS = new Set(['on', 'once', 'addListener']); - -const COMPLETION_METHODS = new Set(['finalMessage', 'done', 'finalText']); - -const TRACKED_STREAM_EVENTS = new Set(['message', 'contentBlock', 'text', 'finalMessage']); - -export class MessageStreamWrapper { +/** + * Proxy wrapper for Anthropic MessageStream objects returned by `.stream()`. + * Preserves the full MessageStream interface (events, completion methods, + * async iteration) while tracking span lifecycle. + */ +class MessageStreamWrapper { private completeResponse: Record = { content: [], model: "", usage: {}, }; - // Assigned via defineHidden in constructor (non-enumerable to avoid circular JSON) private span!: Span; private messageStream!: any; private startTime!: number; private requestKwargs!: Record; private spanContext!: any; - - constructor(span: Span, messageStream: any, startTime: number, requestKwargs: Record, spanContext?: any) { + private parentContext!: any; + private spanFinalized = false; + private completionPending = false; + private listenerMap = new WeakMap>(); + + constructor( + span: Span, + messageStream: any, + startTime: number, + requestKwargs: Record, + spanContext?: any, + parentContext?: any, + ) { defineHidden(this, "span", span); defineHidden(this, "messageStream", messageStream); defineHidden(this, "startTime", startTime); defineHidden(this, "requestKwargs", requestKwargs); - defineHidden(this, "spanContext", spanContext || trace.setSpan(context.active(), span)); - // Use Proxy to delegate all properties and methods to messageStream + defineHidden( + this, + "spanContext", + spanContext || trace.setSpan(context.active(), span), + ); + defineHidden(this, "parentContext", parentContext || context.active()); + + this.registerSafetyNetListeners(); + return new Proxy(this, { get(target, prop, receiver) { - if (prop === 'toJSON') { + if (prop === "toJSON") { return () => target.completeResponse; } - if (typeof prop === 'string' && WRAPPER_OWN_PROPS.has(prop)) { + if (typeof prop === "string" && WRAPPER_OWN_PROPS.has(prop)) { return Reflect.get(target, prop, receiver); } - - // Symbol.asyncIterator - use our custom implementation + if (prop === Symbol.asyncIterator) { return target[Symbol.asyncIterator].bind(target); } - - // Event emitter methods - need special handling to maintain 'this' context - if (typeof prop === 'string' && EVENT_EMITTER_METHODS.has(prop)) { + + if (typeof prop === "string" && EVENT_EMITTER_METHODS.has(prop)) { const method = target.messageStream[prop]; - if (typeof method === 'function') { - if (LISTENER_REGISTRATION_METHODS.has(prop)) { - return function(event: string, listener: Function) { - // Wrap the listener to track events in our span - const wrappedListener = (...args: any[]) => { + if (typeof method !== "function") return method; + + if (LISTENER_REGISTRATION_METHODS.has(prop)) { + return function (event: string, listener: Function) { + const wrappedListener = (...args: any[]) => { + try { target.span.addEvent(`messagestream.event.${event}`, { - 'event.type': event, + "event.type": event, }); - - if (TRACKED_STREAM_EVENTS.has(event)) { - if (args[0]) { - target.processEventData(event, args[0]); - } + if (TRACKED_STREAM_EVENTS.has(event) && args[0]) { + target.processEventData(event, args[0]); } - - return listener(...args); - }; - - return method.call(target.messageStream, event, wrappedListener); + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: event tracking error", + e, + ); + } + return listener(...args); }; - } - return method.bind(target.messageStream); + + let eventMap = target.listenerMap.get(listener); + if (!eventMap) { + eventMap = new Map(); + target.listenerMap.set(listener, eventMap); + } + let wrappers = eventMap.get(event); + if (!wrappers) { + wrappers = []; + eventMap.set(event, wrappers); + } + wrappers.push(wrappedListener); + + return method.call(target.messageStream, event, wrappedListener); + }; } - return method; + if (LISTENER_REMOVAL_METHODS.has(prop)) { + return function (event: string, listener: Function) { + const eventMap = target.listenerMap.get(listener); + const wrappers = eventMap?.get(event); + const wrapped = wrappers?.shift() ?? listener; + if (wrappers && wrappers.length === 0) eventMap?.delete(event); + return method.call(target.messageStream, event, wrapped); + }; + } + if (prop === "removeAllListeners") { + return function (event?: string) { + target.listenerMap = new WeakMap(); + return method.call(target.messageStream, event); + }; + } + return method.bind(target.messageStream); } - - if (typeof prop === 'string' && COMPLETION_METHODS.has(prop)) { + + if (typeof prop === "string" && COMPLETION_METHODS.has(prop)) { const method = target.messageStream[prop]; - if (typeof method === 'function') { - return async function(...args: any[]) { - try { - const result = await method.call(target.messageStream, ...args); - - // When stream completes, finalize our span - if (prop === 'finalMessage' || prop === 'done') { - target.finalizeSpanFromMessage(result); + if (typeof method !== "function") return method; + + return async function (...args: any[]) { + target.completionPending = true; + try { + const result = await method.call(target.messageStream, ...args); + + if (prop === "finalMessage" || prop === "done") { + target.finalizeSpanFromMessage(result); + } else if (prop === "finalText") { + if (typeof result === "string" && result.length > 0) { + target.completeResponse.content = [ + { type: "text", text: result }, + ]; + } else { + target.flushCurrentText(); } - - return result; - } catch (error) { - target.finalizeSpan(SpanStatusCode.ERROR); - throw error; + target.finalizeSpanOnce(SpanStatusCode.OK); } - }; - } - return method; + + return result; + } catch (error) { + target.finalizeSpanOnce(SpanStatusCode.ERROR); + throw error; + } + }; } - - // Everything else - delegate to messageStream + const value = target.messageStream[prop]; - if (typeof value === 'function') { + if (typeof value === "function") return value.bind(target.messageStream); - } return value; - } + }, }); } + private registerSafetyNetListeners(): void { + try { + if (typeof this.messageStream?.on !== "function") return; + + this.messageStream.on("end", () => { + if (!this.completionPending) { + this.finalizeSpanOnce(SpanStatusCode.OK); + } + }); + this.messageStream.on("error", (err: any) => { + if (err && !this.spanFinalized) { + this.span.setStatus({ + code: SpanStatusCode.ERROR, + message: err instanceof Error ? err.message : String(err), + }); + this.span.recordException( + err instanceof Error ? err : new Error(String(err)), + ); + } + this.finalizeSpanOnce(SpanStatusCode.ERROR); + }); + } catch (e) { + Logger.error( + "netra.instrumentation.anthropic: safety net listener registration failed", + e, + ); + } + } + toJSON() { return this.completeResponse; } async *[Symbol.asyncIterator](): AsyncIterator { + let errorOccurred = false; try { for await (const chunk of this.messageStream) { - this.processChunk(chunk); + processStreamChunk(this.completeResponse, chunk, this.span); yield chunk; } - this.finalizeSpan(SpanStatusCode.OK); } catch (err) { + errorOccurred = true; Logger.error("netra.instrumentation.anthropic: Stream error", err); - this.finalizeSpan(SpanStatusCode.ERROR); + this.finalizeSpanOnce(SpanStatusCode.ERROR); throw err; + } finally { + if (!errorOccurred) { + this.finalizeSpanOnce(SpanStatusCode.OK); + } } } @@ -327,34 +345,26 @@ export class MessageStreamWrapper { private processEventData(eventType: string, data: any): void { switch (eventType) { - case 'message': - // This is the message_start event data - if (data.model) { - this.completeResponse.model = data.model; - } - if (data.usage) { - this.completeResponse.usage = data.usage; - } + case "message": + if (data.model) this.completeResponse.model = data.model; + if (data.usage) this.completeResponse.usage = data.usage; break; - - case 'text': - // Accumulate text + + case "text": if (!this.completeResponse.currentText) { - this.completeResponse.currentText = ''; + this.completeResponse.currentText = ""; } this.completeResponse.currentText += data; break; - - case 'contentBlock': - // Track content blocks + + case "contentBlock": if (!this.completeResponse.content) { this.completeResponse.content = []; } this.completeResponse.content.push(data); break; - - case 'finalMessage': - // Final message contains everything + + case "finalMessage": if (data.model) this.completeResponse.model = data.model; if (data.content) this.completeResponse.content = data.content; if (data.usage) this.completeResponse.usage = data.usage; @@ -362,296 +372,424 @@ export class MessageStreamWrapper { } } - private processChunk(chunk: any): void { - /** - * Anthropic streaming events look like: - * - message_start - * - content_block_start - * - content_block_delta - * - content_block_stop - * - message_delta - * - message_stop - */ - - switch (chunk.type) { - case "message_start": { - if (chunk.message?.model) { - this.completeResponse.model = chunk.message.model; - } - if (chunk.message?.usage) { - this.completeResponse.usage = chunk.message.usage; - } - break; - } - - case "content_block_start": { - if (!this.completeResponse.content) { - this.completeResponse.content = []; - } - const block = chunk.content_block; - if (block.type === "tool_use") { - this.completeResponse.content.push({ - type: "tool_use", - id: block.id, - name: block.name, - input: "", - }); - } else { - this.completeResponse.content.push({ - type: block.type, - text: "", - }); - } - break; - } - - case "content_block_delta": { - if (!this.completeResponse.content || this.completeResponse.content.length === 0) { - this.completeResponse.content = [{ type: 'text', text: '' }]; - } - - const lastBlock = - this.completeResponse.content[ - this.completeResponse.content.length - 1 - ]; - - if (chunk.delta?.type === "input_json_delta" && lastBlock?.type === "tool_use") { - lastBlock.input += chunk.delta.partial_json ?? ""; - } else if (lastBlock && chunk.delta?.text) { - lastBlock.text += chunk.delta.text; - } - break; - } - - case "content_block_stop": { - const blocks = this.completeResponse.content; - if (blocks && blocks.length > 0) { - const finishedBlock = blocks[blocks.length - 1]; - if (finishedBlock?.type === "tool_use" && typeof finishedBlock.input === "string") { - try { - finishedBlock.input = JSON.parse(finishedBlock.input); - } catch { - Logger.warn("netra.instrumentation.anthropic: Failed to parse tool use input", finishedBlock.input); - } - } - } - break; - } - - case "message_delta": { - if (chunk.delta?.usage) { - this.completeResponse.usage = { - ...this.completeResponse.usage, - ...chunk.delta.usage, - }; - } - break; - } - - case "message_stop": { - if (chunk.usage) { - this.completeResponse.usage = chunk.usage; - } - break; - } + private flushCurrentText(): void { + if ( + this.completeResponse.currentText && + (!this.completeResponse.content || + this.completeResponse.content.length === 0) + ) { + this.completeResponse.content = [ + { type: "text", text: this.completeResponse.currentText }, + ]; } - - this.span.addEvent("llm.content.completion.chunk", { - "chunk.type": chunk.type, - }); } private finalizeSpanFromMessage(message: any): void { - // Extract from final message if available if (message) { if (message.model) this.completeResponse.model = message.model; if (message.content) this.completeResponse.content = message.content; if (message.usage) this.completeResponse.usage = message.usage; + if (message.stop_reason) + this.completeResponse.stop_reason = message.stop_reason; } - - this.finalizeSpan(SpanStatusCode.OK); + this.finalizeSpanOnce(SpanStatusCode.OK); } - private finalizeSpan(code: SpanStatusCode): void { - const endTime = Date.now(); - const duration = (endTime - this.startTime) / 1000; - - setResponseAttributes(this.span, { - model: this.completeResponse.model, - content: this.completeResponse.content, - usage: this.completeResponse.usage, - }); - - this.span.setAttribute("llm.response.duration", duration); - this.span.setStatus({ code }); - this.span.end(); + private finalizeSpanOnce(code: SpanStatusCode): void { + if (this.spanFinalized) return; + this.spanFinalized = true; + finalizeStreamSpan(this.span, this.completeResponse, this.startTime, code); } } -export class AsyncStreamingWrapper - implements AsyncIterable, AsyncIterator -{ - private iterator: AsyncIterator | null = null; - private completeResponse: Record = { - choices: [], - model: "", - }; - // Assigned via defineHidden in constructor (non-enumerable to avoid circular JSON) - private span!: Span; - private response!: any; - private startTime!: number; - private requestKwargs!: Record; - private spanContext!: any; +/** + * Shimmer-compatible wrapper factory for `.create()` methods. + * Returns `(original) => replacement` as expected by `shimmer.wrap()`. + */ +function anthropicWrapper( + tracer: Tracer, + spanName: string, + requestType: AnthropicRequestType, +) { + return function wrapper any>(original: F): F { + return function (this: unknown, ...args: any[]) { + if (shouldSuppressInstrumentation()) { + return original.apply(this, args); + } - constructor(span: Span, response: any, startTime: number, requestKwargs: Record, spanContext?: any) { - defineHidden(this, "span", span); - defineHidden(this, "response", response); - defineHidden(this, "startTime", startTime); - defineHidden(this, "requestKwargs", requestKwargs); - defineHidden(this, "spanContext", spanContext || trace.setSpan(context.active(), span)); - } + const attributes = (args[0] || {}) as Record; + const currentContext = context.active(); + const isStreaming = attributes.stream === true; - toJSON() { - return this.completeResponse; - } + const activeSpan = trace.getSpan(currentContext); + Logger.debug( + `Anthropic invoke (${requestType}). Active TraceId: ${activeSpan?.spanContext().traceId}, SpanId: ${activeSpan?.spanContext().spanId}`, + ); - [Symbol.asyncIterator](): AsyncIterator { - return this; - } + return tracer.startActiveSpan( + spanName, + { + kind: SpanKind.CLIENT, + attributes: { "llm.request.type": requestType }, + }, + (span: Span) => { + try { + setRequestAttributes(span, attributes, requestType); + if (isStreaming) { + span.setAttribute("llm.streaming", true); + } + const startTime = Date.now(); + const spanContext = trace.setSpan(currentContext, span); + const response = context.with(spanContext, () => + original.apply(this, args), + ); + + const completeResponse: Record = { + content: [], + model: "", + usage: {}, + }; - async next(): Promise> { - try { - if (!this.iterator) { - if (Symbol.asyncIterator in this.response) { - this.iterator = (this.response as AsyncIterable)[ - Symbol.asyncIterator - ](); - } else if ( - typeof (this.response as AsyncIterator).next === "function" - ) { - this.iterator = this.response as AsyncIterator; - } else { - throw new Error("Response is not iterable"); - } + return wrapResponse( + response, + { + withContext: (fn) => context.with(spanContext, fn), + onChunk: (chunk) => + processStreamChunk(completeResponse, chunk, span), + onError: (error) => { + Logger.error("netra.instrumentation.anthropic:", error); + span.setStatus({ + code: SpanStatusCode.ERROR, + message: + error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + }, + onSuccess: (value) => { + const endTime = Date.now(); + const responseDict = modelAsDict(value); + setResponseAttributes(span, responseDict); + span.setAttribute( + "llm.response.duration", + (endTime - startTime) / 1000, + ); + }, + finalize: (status) => { + const hasStreamData = + completeResponse.content?.length || + completeResponse.model || + completeResponse.usage?.input_tokens !== undefined || + completeResponse.usage?.output_tokens !== undefined; + if (status === "ok" && hasStreamData) { + finalizeStreamSpan( + span, + completeResponse, + startTime, + SpanStatusCode.OK, + ); + } else { + if (status === "ok") { + span.setStatus({ code: SpanStatusCode.OK }); + } + span.end(); + } + }, + }, + { preserveOriginal: response }, + ); + } catch (error) { + Logger.error("netra.instrumentation.anthropic:", error); + span.setStatus({ + code: SpanStatusCode.ERROR, + message: error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + }, + ); + } as unknown as F; + }; +} + +/** + * Shimmer-compatible wrapper factory for `.stream()` methods. + * `originalCreate` is the unpatched `create` method captured before patching, + * used to build a per-call Proxy so `.stream()` calls the uninstrumented + * `create` internally (avoids double-spanning). + */ +function streamWrapper( + tracer: Tracer, + spanName: string, + requestType: AnthropicRequestType, + originalCreate?: Function, +) { + return function wrapper any>(original: F): F { + return function (this: unknown, ...args: any[]) { + if (shouldSuppressInstrumentation()) { + return original.apply(this, args); } - const result = await context.with(this.spanContext, () => this.iterator!.next()); - if (result.done) { - this.finalizeSpan(SpanStatusCode.OK); - return result; + const attributes = (args[0] || {}) as Record; + const currentContext = context.active(); + + const span = tracer.startSpan( + spanName, + { + kind: SpanKind.CLIENT, + attributes: { + "llm.request.type": requestType, + "llm.streaming": true, + "llm.operation": "stream", + }, + }, + currentContext, + ); + + const spanContext = trace.setSpan(currentContext, span); + setRequestAttributes(span, attributes, requestType); + const startTime = Date.now(); + + const callTarget = originalCreate + ? new Proxy(this as any, { + get(target, prop) { + // Using the uninstrumented create method to avoid double-spanning, since `.stream()` calls `.create()` internally. + if (prop === "create") return originalCreate.bind(target); + // All other methods bound to the target object. + const value = target[prop]; + if (typeof value === "function") return value.bind(target); + return value; + }, + }) + : this; + + try { + const messageStream = context.with(spanContext, () => + original.call(callTarget, ...args), + ); + return new MessageStreamWrapper( + span, + messageStream, + startTime, + attributes, + spanContext, + currentContext, + ); + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; } - this.processChunk(result.value); - return result; - } catch (error) { - this.finalizeSpan(SpanStatusCode.ERROR); - throw error; - } - } + } as unknown as F; + }; +} - private processChunk(chunk: any): void { - // Reusing the same chunk processing logic as MessageStreamWrapper, but adapted for this context - // The raw chunks from messages.create({stream:true}) are the same as what MessageStreamWrapper handles. - - switch (chunk.type) { - case "message_start": { - if (chunk.message?.model) { - this.completeResponse.model = chunk.message.model; - } - if (chunk.message?.usage) { - this.completeResponse.usage = chunk.message.usage; - } - break; +/** + * Shimmer-compatible wrapper factory for `.toolRunner()`. + * Wraps the returned ToolRunner with a Proxy that manages + * span lifecycle across async iteration and thenable resolution. + */ +function toolRunnerWrapper( + tracer: Tracer, + spanName: string, + requestType: AnthropicRequestType, +) { + return function wrapper any>(original: F): F { + return function (this: unknown, ...args: any[]) { + if (shouldSuppressInstrumentation()) { + return original.apply(this, args); } - case "content_block_start": { - const content = this.completeResponse.content as any[] || []; - this.completeResponse.content = content; - const block = chunk.content_block; - if (block.type === "tool_use") { - content.push({ - type: "tool_use", - id: block.id, - name: block.name, - input: "", - }); + const attributes = (args[0] || {}) as Record; + const currentContext = context.active(); + const span = tracer.startSpan( + spanName, + { + kind: SpanKind.CLIENT, + attributes: { + "llm.request.type": requestType, + "netra.span.type": "AGENT", + "llm.operation": "tool.runner", + }, + }, + currentContext, + ); + + let spanEnded = false; + const endSpanOnce = (code: SpanStatusCode, error?: Error) => { + if (spanEnded) return; + spanEnded = true; + if (error) { + span.setStatus({ code, message: error.message }); + span.recordException(error); } else { - content.push({ - type: block.type, - text: "", - }); + span.setStatus({ code }); } - break; - } + span.end(); + }; - case "content_block_delta": { - const content = this.completeResponse.content as any[] || []; - if (content.length === 0) { - content.push({ type: 'text', text: '' }); - this.completeResponse.content = content; - } - - const lastBlock = content[content.length - 1]; + try { + setRequestAttributes(span, attributes, "beta"); + const spanContext = trace.setSpan(currentContext, span); - if (chunk.delta?.type === "input_json_delta" && lastBlock?.type === "tool_use") { - lastBlock.input += chunk.delta.partial_json ?? ""; - } else if (lastBlock && chunk.delta?.text) { - lastBlock.text += chunk.delta.text; + const wrappedTools = Array.isArray(attributes.tools) + ? wrapRunnableTools(attributes.tools as any[], tracer, spanContext) + : attributes.tools; + + const wrappedArgs = [ + { ...attributes, tools: wrappedTools }, + ...args.slice(1), + ]; + const runner = context.with(spanContext, () => + original.apply(this, wrappedArgs), + ); + + if (runner == null) { + endSpanOnce(SpanStatusCode.OK); + return runner; } - break; - } - case "content_block_stop": { - const content = this.completeResponse.content as any[] || []; - if (content.length > 0) { - const finishedBlock = content[content.length - 1]; - if (finishedBlock?.type === "tool_use" && typeof finishedBlock.input === "string") { - try { - finishedBlock.input = JSON.parse(finishedBlock.input); - } catch { - Logger.warn("netra.instrumentation.anthropic: Failed to parse tool use input", finishedBlock.input); + return new Proxy(runner, { + get(target: any, prop: string | symbol, receiver: any) { + if (prop === Symbol.asyncIterator) { + return function () { + const originalIterator = target[Symbol.asyncIterator](); + return { + [Symbol.asyncIterator]() { + return this; + }, + async next() { + try { + const result = await context.with(spanContext, () => + originalIterator.next(), + ); + if (result.done) endSpanOnce(SpanStatusCode.OK); + return result; + } catch (error) { + endSpanOnce(SpanStatusCode.ERROR, error as Error); + throw error; + } + }, + async return(value?: any) { + try { + const result = await (originalIterator.return?.( + value, + ) ?? { + done: true, + value, + }); + return result; + } finally { + endSpanOnce(SpanStatusCode.OK); + } + }, + async throw(error?: any) { + const err = + error instanceof Error ? error : new Error(String(error)); + if (originalIterator.throw) { + try { + const result = await originalIterator.throw(error); + if (result.done) { + endSpanOnce(SpanStatusCode.ERROR, err); + } + return result; + } catch (e) { + endSpanOnce( + SpanStatusCode.ERROR, + e instanceof Error ? e : new Error(String(e)), + ); + throw e; + } + } + endSpanOnce(SpanStatusCode.ERROR, err); + throw error; + }, + }; + }; } - } - } - break; - } - case "message_delta": { - if (chunk.delta?.usage) { - const currentUsage = this.completeResponse.usage as any || {}; - this.completeResponse.usage = { - ...currentUsage, - ...chunk.delta.usage, - }; - } - break; - } + if (prop === "then" || prop === "catch" || prop === "finally") { + const originalMethod = target[prop]; + if (typeof originalMethod !== "function") return originalMethod; + + if (prop === "then") { + return function ( + onFulfilled?: Function, + onRejected?: Function, + ) { + return originalMethod.call( + target, + (v: any) => { + endSpanOnce(SpanStatusCode.OK); + return onFulfilled ? onFulfilled(v) : v; + }, + (e: any) => { + endSpanOnce( + SpanStatusCode.ERROR, + e instanceof Error ? e : new Error(String(e)), + ); + if (onRejected) return onRejected(e); + throw e; + }, + ); + }; + } + if (prop === "catch") { + return function (onRejected?: Function) { + return receiver.then(undefined, onRejected); + }; + } + if (prop === "finally") { + return function (onFinally?: Function) { + return receiver.then( + (v: any) => { + onFinally?.(); + return v; + }, + (e: any) => { + onFinally?.(); + throw e; + }, + ); + }; + } + } - case "message_stop": { - if (chunk.usage) { - this.completeResponse.usage = chunk.usage; - } - break; + const value = target[prop]; + if (typeof value === "function") return value.bind(target); + return value; + }, + }); + } catch (error) { + endSpanOnce( + SpanStatusCode.ERROR, + error instanceof Error ? error : new Error(String(error)), + ); + throw error; } - } + } as unknown as F; + }; +} - this.span.addEvent("llm.content.completion.chunk", { - "chunk.type": chunk.type, - }); - } +export const chatWrapper = (tracer: Tracer) => + anthropicWrapper(tracer, SPAN_NAMES.CHAT, "chat"); - private finalizeSpan(code: SpanStatusCode): void { - const endTime = Date.now(); - const duration = (endTime - this.startTime) / 1000; - - // We match the format expected by setResponseAttributes - setResponseAttributes(this.span, { - model: this.completeResponse.model, - content: this.completeResponse.content, - usage: this.completeResponse.usage, - }); +export const betaWrapper = (tracer: Tracer) => + anthropicWrapper(tracer, SPAN_NAMES.BETA, "beta"); - this.span.setAttribute("llm.response.duration", duration); - this.span.setStatus({ code }); - this.span.end(); - } -} +export const batchesWrapper = (tracer: Tracer) => + anthropicWrapper(tracer, SPAN_NAMES.BATCHES, "batches"); + +export const chatStreamWrapper = (tracer: Tracer, originalCreate?: Function) => + streamWrapper(tracer, SPAN_NAMES.STREAM, "chat", originalCreate); + +export const betaStreamWrapper = (tracer: Tracer, originalCreate?: Function) => + streamWrapper(tracer, SPAN_NAMES.BETA_STREAM, "beta", originalCreate); + +export const betaToolRunnerWrapper = (tracer: Tracer) => + toolRunnerWrapper(tracer, SPAN_NAMES.BETA_TOOL_RUNNER, "beta"); diff --git a/src/instrumentation/index.ts b/src/instrumentation/index.ts index d77dd3e..7c58268 100644 --- a/src/instrumentation/index.ts +++ b/src/instrumentation/index.ts @@ -18,6 +18,7 @@ import { } from "../config"; import { Logger } from "../logger"; import { + AttributeSizeLimitProcessor, InstrumentationSpanProcessor, LlmTraceIdentifierSpanProcessor, RootSpanProcessor, @@ -549,7 +550,7 @@ async function initCustomInstrumentationsAsync( if (customInstrumentModules.anthropic) { try { - await anthropicInstrumentor.instrumentAsync({ tracerProvider }); + await anthropicInstrumentor.instrument({ tracerProvider }); Logger.debug("Custom Anthropic instrumentation enabled"); } catch (e) { Logger.debug("Failed to initialize custom Anthropic instrumentation:", e); @@ -815,7 +816,7 @@ function addCustomSpanProcessors( provider.addSpanProcessor(instrumentationProcessor); // 2. Session Span Processor - adds session context (session_id, user_id, etc.) - const sessionProcessor = new SessionSpanProcessor(); + const sessionProcessor = new SessionSpanProcessor(config.environment); provider.addSpanProcessor(sessionProcessor); // 3. Span I/O Processor - normalises input/output from gen_ai.prompt/completion @@ -843,6 +844,14 @@ function addCustomSpanProcessors( provider.addSpanProcessor(scrubbingProcessor); } + // 7. Attribute Size Limit Processor - enforces hard size limits on span + // attributes before export to prevent "entity too large" errors. + // MUST be last so it acts as final gate after all other processors. + const sizeLimitProcessor = new AttributeSizeLimitProcessor( + Config.SPAN_ATTRIBUTE_MAX_SIZE, + ); + provider.addSpanProcessor(sizeLimitProcessor); + Logger.debug("Custom span processors registered successfully"); return provider; diff --git a/src/instrumentation/span-attributes.ts b/src/instrumentation/span-attributes.ts index 867d924..5b63bda 100644 --- a/src/instrumentation/span-attributes.ts +++ b/src/instrumentation/span-attributes.ts @@ -11,12 +11,17 @@ export const SpanAttributes = { LLM_REQUEST_TOP_P: "gen_ai.request.top_p", LLM_REQUEST_REASONING: "gen_ai.request.reasoning", LLM_REQUEST_REASONING_EFFORT: "gen_ai.request.reasoning_effort", + LLM_REQUEST_TOOL_NAME: "gen_ai.request.tool.name", + LLM_REQUEST_TOOL_ID: "gen_ai.request.tool.id", LLM_RESPONSE_MODEL: "gen_ai.response.model", + LLM_RESPONSE_FINISH_REASON: "llm.response.finish_reason", LLM_USAGE_PROMPT_TOKENS: "gen_ai.usage.prompt_tokens", LLM_USAGE_COMPLETION_TOKENS: "gen_ai.usage.completion_tokens", LLM_USAGE_CACHE_READ_INPUT_TOKENS: "gen_ai.usage.cache_read_input_tokens", + LLM_USAGE_CACHE_CREATION_INPUT_TOKENS: + "gen_ai.usage.cache_creation_input_tokens", LLM_USAGE_REASONING_TOKENS: "gen_ai.usage.reasoning_tokens", LLM_USAGE_TOTAL_TOKENS: "llm.usage.total_tokens", diff --git a/src/instrumentation/utils.ts b/src/instrumentation/utils.ts index 82468a5..18cdc80 100644 --- a/src/instrumentation/utils.ts +++ b/src/instrumentation/utils.ts @@ -6,7 +6,9 @@ import { Span, context } from "@opentelemetry/api"; import { Config } from "../config"; import { Logger } from "../logger"; +import { safeStringify } from "../utils/serialization"; import { SpanAttributes } from "./span-attributes"; + /** * Controls where native traces are sent. * @@ -41,10 +43,8 @@ export function shouldSuppressInstrumentation(): boolean { return ctx.getValue(SUPPRESS_INSTRUMENTATION_KEY) === true; } -// Type Utilities -export function isPromise(value: unknown): value is Promise { - return value instanceof Promise; -} +// Type Utilities — re-export from canonical location to avoid duplication +export { isPromise } from "../utils/response-handler"; /** * Define a non-enumerable, writable, configurable property on `target`. @@ -98,8 +98,7 @@ export interface TracedMessage { content: string; } -// Internal Helpers -function isTraceContentEnabled(): boolean { +export function isTraceContentEnabled(): boolean { const raw = process.env.TRACELOOP_TRACE_CONTENT ?? process.env.NETRA_TRACE_CONTENT ?? @@ -107,20 +106,6 @@ function isTraceContentEnabled(): boolean { return ["1", "true"].includes(String(raw).toLowerCase()); } -function safeStringify(value: unknown): string { - if (typeof value === "string") return value; - try { - return JSON.stringify(value); - } catch { - return String(value); - } -} - -function truncate(value: string, maxLen: number): string { - if (!value || value.length <= maxLen) return value; - return value.slice(0, maxLen) + "...(truncated)"; -} - /** * Returns true if `value` represents meaningful content worth recording. * Guards against setting empty-string attributes on spans. @@ -172,7 +157,7 @@ export function buildInputMessages( ): TracedMessage[] { const messages: TracedMessage[] = []; - if (requestType === "chat") { + if (requestType === "chat" || requestType === "beta") { if (hasContent(kwargs.system)) { const systemContent = typeof kwargs.system === "string" @@ -184,12 +169,41 @@ export function buildInputMessages( const rawMessages = kwargs.messages; if (!Array.isArray(rawMessages)) return messages; for (const msg of rawMessages) { - if (!isDict(msg)) continue; - if (hasContent(msg.role) && hasContent(msg.content)) { + if (!isDict(msg) || !hasContent(msg.role) || !hasContent(msg.content)) { + continue; + } + + if (msg.role !== "user" || !Array.isArray(msg.content)) { messages.push({ role: msg.role, content: safeStringify(msg.content), }); + continue; + } + + const isToolResult = (b: unknown): b is Record => + isDict(b) && b.type === "tool_result"; + + const userBlocks = msg.content.filter((b) => !isToolResult(b)); + + if (userBlocks.length) { + messages.push({ + role: "user", + content: safeStringify(userBlocks), + }); + } + + for (const block of msg.content) { + if (!isToolResult(block)) continue; + + messages.push({ + role: "tool", + content: safeStringify({ + tool_use_id: block.tool_use_id, + content: block.content, + is_error: block.is_error ?? false, + }, Config.CONVERSATION_MAX_LEN), + }); } } } else if (requestType === "response") { @@ -220,10 +234,7 @@ export function buildInputMessages( // Embeddings / genericinput const input = kwargs.input ?? kwargs.inputs; if (hasContent(input)) { - const content = truncate( - safeStringify(input), - Config.CONVERSATION_MAX_LEN, - ); + const content = safeStringify(input, Config.CONVERSATION_MAX_LEN); messages.push({ role: "user", content }); } } @@ -324,7 +335,7 @@ export function buildOutputMessages( } else if (block.type === "tool_use" && block.name) { messages.push({ role: "tool", - content: JSON.stringify({ name: block.name, input: block.input }), + content: JSON.stringify({ id: block.id, name: block.name, input: block.input }), }); } } @@ -345,13 +356,14 @@ export function writePromptAttributes( if (messages.length === 0) return; for (let i = 0; i < messages.length; i++) { + const msg = messages[i]; span.setAttribute( `${SpanAttributes.LLM_PROMPTS}.${i}.role`, - messages[i].role, + msg.role, ); span.setAttribute( `${SpanAttributes.LLM_PROMPTS}.${i}.content`, - messages[i].content, + msg.content, ); } @@ -412,7 +424,6 @@ export function writeCompletionAttributes( span.setAttribute("output", JSON.stringify(messages)); } - // Request Attributes export function setRequestAttributes( span: Span, @@ -433,6 +444,11 @@ export function setRequestAttributes( // Standard model parameters setModelParams(span, kwargs); + // Tool definitions + if (Array.isArray(kwargs.tools)) { + span.setAttribute("tools", safeStringify(kwargs.tools, Config.ATTRIBUTE_MAX_LEN)); + } + // Reasoning config if (kwargs.reasoning !== undefined) { span.setAttribute( @@ -450,7 +466,7 @@ export function setRequestAttributes( if (kwargs.suffix !== undefined) { span.setAttribute( "llm.request.suffix", - truncate(safeStringify(kwargs.suffix), Config.CONVERSATION_MAX_LEN), + safeStringify(kwargs.suffix, Config.CONVERSATION_MAX_LEN), ); } } @@ -492,15 +508,23 @@ export function setResponseAttributes( // Response Sub-helpers function setFinishReason(span: Span, response: Record): void { + if (response.stop_reason) { + span.setAttribute( + SpanAttributes.LLM_RESPONSE_FINISH_REASON, + String(response.stop_reason), + ); + span.setAttribute("gen_ai.response.finish_reason", String(response.stop_reason)); + } + const choices = response.choices as | Array> | undefined; - if (!Array.isArray(choices) || choices.length === 0) return; - - const reason = choices[0].finish_reason ?? choices[0].finishReason; - if (reason) { - span.setAttribute("gen_ai.response.finish_reason", String(reason)); - span.setAttribute("llm.response.finish_reason", String(reason)); + if (Array.isArray(choices) && choices.length > 0) { + const reason = choices[0].finish_reason ?? choices[0].finishReason; + if (reason) { + span.setAttribute(SpanAttributes.LLM_RESPONSE_FINISH_REASON, String(reason)); + span.setAttribute("gen_ai.response.finish_reason", String(reason)); + } } } @@ -537,15 +561,25 @@ function setUsageAttributes( ); } - const cacheTokens = ( - (usage.prompt_tokens_details ?? usage.input_tokens_details) as - | { cached_tokens?: unknown } - | undefined - )?.cached_tokens; - if (cacheTokens !== undefined) { + const cacheReadTokens = + usage.cache_read_input_tokens ?? + ( + (usage.prompt_tokens_details ?? usage.input_tokens_details) as + | { cached_tokens?: unknown } + | undefined + )?.cached_tokens; + if (cacheReadTokens !== undefined) { span.setAttribute( SpanAttributes.LLM_USAGE_CACHE_READ_INPUT_TOKENS, - Number(cacheTokens), + Number(cacheReadTokens), + ); + } + + const cacheCreationTokens = usage.cache_creation_input_tokens; + if (cacheCreationTokens !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_CACHE_CREATION_INPUT_TOKENS, + Number(cacheCreationTokens), ); } diff --git a/src/logger.ts b/src/logger.ts index 509189b..205b88b 100644 --- a/src/logger.ts +++ b/src/logger.ts @@ -21,6 +21,10 @@ export class Logger { ); } + static isDebugMode(): boolean { + return this.isDebug; + } + static debug(...args: any[]): void { if (this.isDebug) console.debug(PREFIX, ...args); } diff --git a/src/processors/attribute-size-limit-processor.ts b/src/processors/attribute-size-limit-processor.ts new file mode 100644 index 0000000..f274d64 --- /dev/null +++ b/src/processors/attribute-size-limit-processor.ts @@ -0,0 +1,75 @@ +/** + * Attribute Size Limit Span Processor + * + * Enforces a hard max length on every span attribute value via setAttribute + * wrapping in onStart. Prevents "entity too large" errors during export. + */ + +import { AttributeValue, Context, Span } from "@opentelemetry/api"; +import { ReadableSpan, SpanProcessor } from "@opentelemetry/sdk-trace-base"; +import { Logger } from "../logger"; + +const DEFAULT_MAX_ATTRIBUTE_SIZE = 32_000; // 32KB per attribute + +type SetAttributeFn = (key: string, value: AttributeValue) => Span; + +export class AttributeSizeLimitProcessor implements SpanProcessor { + private maxAttributeSize: number; + + constructor(maxAttributeSize?: number) { + this.maxAttributeSize = maxAttributeSize ?? DEFAULT_MAX_ATTRIBUTE_SIZE; + } + + onStart(span: Span, _parentContext: Context): void { + try { + this._wrapSetAttribute(span); + } catch (e) { + Logger.debug("AttributeSizeLimitProcessor.onStart error:", e); + } + } + + onEnd(_span: ReadableSpan): void {} + + shutdown(): Promise { + return Promise.resolve(); + } + + forceFlush(): Promise { + return Promise.resolve(); + } + + private _wrapSetAttribute(span: Span): void { + const original: SetAttributeFn = span.setAttribute.bind(span); + const maxLen = this.maxAttributeSize; + + const patched = (key: string, value: AttributeValue): Span => { + try { + return original(key, truncateValue(value, maxLen) as AttributeValue); + } catch { + try { + return original(key, value); + } catch { + return span; + } + } + }; + + (span as any).setAttribute = patched; + } +} + +function truncateValue(value: unknown, maxLen: number): unknown { + if (typeof value === "string") { + return value.length > maxLen ? value.substring(0, maxLen) : value; + } + + if (Array.isArray(value)) { + const serialized = JSON.stringify(value); + if (serialized.length > maxLen) { + return serialized.substring(0, maxLen); + } + return value; + } + + return value; +} diff --git a/src/processors/index.ts b/src/processors/index.ts index d0e186a..70df132 100644 --- a/src/processors/index.ts +++ b/src/processors/index.ts @@ -5,6 +5,7 @@ * attribute management, session tracking, and sensitive data scrubbing. */ +export { AttributeSizeLimitProcessor } from "./attribute-size-limit-processor"; export { InstrumentationSpanProcessor } from "./instrumentation-span-processor"; export { LlmTraceIdentifierSpanProcessor } from "./llm-trace-identifier-span-processor"; export { withBlockedSpansLocal } from "./localfiltering-span-processor"; diff --git a/src/processors/session-span-processor.ts b/src/processors/session-span-processor.ts index aaed2c7..d274607 100644 --- a/src/processors/session-span-processor.ts +++ b/src/processors/session-span-processor.ts @@ -129,6 +129,12 @@ export function clearSessionBaggage(): void { } export class SessionSpanProcessor implements SpanProcessor { + private readonly environment: string; + + constructor(environment: string = "local") { + this.environment = environment; + } + /** * Called when a span starts. Adds session and entity context attributes. */ @@ -138,6 +144,10 @@ export class SessionSpanProcessor implements SpanProcessor { span.setAttribute("library.name", Config.LIBRARY_NAME); span.setAttribute("library.version", Config.LIBRARY_VERSION); span.setAttribute("sdk.name", Config.SDK_NAME); + // Intentional: set per-span in addition to OTEL_RESOURCE_ATTRIBUTES + // because this processor may be added to a pre-existing TracerProvider + // whose Resource was already frozen without these attributes. + span.setAttribute("deployment.environment", this.environment); // Get baggage from the parent context (or current if not provided) const ctxToUse = parentContext || context.active(); diff --git a/src/session-manager.ts b/src/session-manager.ts index 6597d03..f66634c 100644 --- a/src/session-manager.ts +++ b/src/session-manager.ts @@ -13,6 +13,7 @@ import { Config } from "./config"; import { Logger } from "./logger"; import { RootSpanProcessor } from "./processors/root-span-processor"; import { ConversationType } from "./types"; +import { serializeValue } from "./utils/serialization"; export { ConversationType }; @@ -61,15 +62,6 @@ export function runWithEntityContext(fn: () => T): T { return entityStorage.run(ctx, fn); } -// Internal serialization - -function serializeValue(value: any): string { - if (typeof value === "string") { - return value.substring(0, Config.ATTRIBUTE_MAX_LEN); - } - return JSON.stringify(value).substring(0, Config.ATTRIBUTE_MAX_LEN); -} - // SessionManager export class SessionManager { @@ -187,7 +179,10 @@ export class SessionManager { */ static setInput(value: any): void { try { - SessionManager.setAttributeOnActiveSpan("netra.user.input", serializeValue(value)); + SessionManager.setAttributeOnActiveSpan( + "netra.user.input", + serializeValue(value, Config.ATTRIBUTE_MAX_LEN), + ); } catch (e) { Logger.error("setInput failed:", e); } @@ -200,7 +195,10 @@ export class SessionManager { */ static setOutput(value: any): void { try { - SessionManager.setAttributeOnActiveSpan("netra.user.output", serializeValue(value)); + SessionManager.setAttributeOnActiveSpan( + "netra.user.output", + serializeValue(value, Config.ATTRIBUTE_MAX_LEN), + ); } catch (e) { Logger.error("setOutput failed:", e); } @@ -213,7 +211,10 @@ export class SessionManager { */ static setRootInput(value: any): void { try { - RootSpanProcessor.setAttributeOnRootSpan("netra.user.input", serializeValue(value)); + RootSpanProcessor.setAttributeOnRootSpan( + "netra.user.input", + serializeValue(value, Config.ATTRIBUTE_MAX_LEN), + ); } catch (e) { Logger.error("setRootInput failed:", e); } @@ -226,7 +227,10 @@ export class SessionManager { */ static setRootOutput(value: any): void { try { - RootSpanProcessor.setAttributeOnRootSpan("netra.user.output", serializeValue(value)); + RootSpanProcessor.setAttributeOnRootSpan( + "netra.user.output", + serializeValue(value, Config.ATTRIBUTE_MAX_LEN), + ); } catch (e) { Logger.error("setRootOutput failed:", e); } diff --git a/src/utils/response-handler.ts b/src/utils/response-handler.ts new file mode 100644 index 0000000..1c7a5d3 --- /dev/null +++ b/src/utils/response-handler.ts @@ -0,0 +1,234 @@ +import { Logger } from "../logger"; + +export interface ResponseCallbacks { + withContext(fn: () => T): T; + onChunk?(chunk: TChunk): void; + onError(error: unknown): void; + onSuccess?(value: unknown): void; + finalize(status: "ok" | "error"): void; +} + +export function isAsyncIterable( + value: unknown, +): value is AsyncIterable { + return ( + value != null && typeof (value as any)[Symbol.asyncIterator] === "function" + ); +} + +export function isPromise(value: unknown): value is Promise { + return value != null && typeof (value as any).then === "function"; +} + +const ITERATOR_METHODS = new Set(["next", "return", "throw"]); + +/** + * Wrap an async iterable with lifecycle callbacks. + * Returns a Proxy that preserves the original object's full interface + * while intercepting iteration methods. + * + * When `onChunk` is provided, each yielded value is passed to it + * (enabling LLM response accumulation). When omitted, chunks pass through + * untouched (lifecycle-only mode). + */ +export function wrapAsyncIterable( + source: AsyncIterable, + callbacks: ResponseCallbacks, +): any { + function createWrappedIterator(): AsyncIterator { + const iterator = source[Symbol.asyncIterator](); + let done = false; + + const safeFinalize = (status: "ok" | "error") => { + if (done) return; + done = true; + try { + callbacks.finalize(status); + } catch (e) { + Logger.error("netra: finalize callback error", e); + } + }; + + return { + async next(value?: any) { + try { + const result = await callbacks.withContext(() => iterator.next(value)); + if (!result.done) { + try { + callbacks.onChunk?.(result.value); + } catch (e) { + Logger.error("netra: onChunk callback error", e); + } + } else { + safeFinalize("ok"); + } + return result; + } catch (e: any) { + try { + callbacks.onError(e); + } catch { + Logger.error("netra: onError callback error", e); + } + safeFinalize("error"); + throw e; + } + }, + async return(value?: any) { + try { + const result = await callbacks.withContext( + () => iterator.return?.(value) ?? { done: true as const, value }, + ); + safeFinalize("ok"); + return result; + } catch (e: any) { + try { + callbacks.onError(e); + } catch { + Logger.error("netra: onError callback error", e); + } + safeFinalize("error"); + throw e; + } + }, + async throw(e?: any) { + try { + const result = await callbacks.withContext(() => { + if (iterator.throw) return iterator.throw(e); + throw e; + }); + if (result.done) safeFinalize("ok"); + return result; + } catch (err) { + try { + callbacks.onError(err); + } catch { + Logger.error("netra: onError callback error", err); + } + safeFinalize("error"); + throw err; + } + }, + }; + } + + let directIterator: AsyncIterator | null = null; + + return new Proxy(source, { + get(target, prop) { + if (prop === Symbol.asyncIterator) { + return () => createWrappedIterator(); + } + if (typeof prop === "string" && ITERATOR_METHODS.has(prop)) { + if (!directIterator) directIterator = createWrappedIterator(); + return (directIterator as any)[prop].bind(directIterator); + } + const value = (target as any)[prop]; + if (typeof value === "function") return value.bind(target); + return value; + }, + }); +} + +/** + * Wrap a promise with lifecycle callbacks. + * If the resolved value is async-iterable, wraps it with `wrapAsyncIterable`. + * When `preserveOriginal` is set, returns a Proxy that routes + * then/catch/finally to the instrumented promise and other properties + * to the original object (preserving SDK methods like `.withResponse()`). + */ +export function wrapPromise( + promise: Promise, + callbacks: ResponseCallbacks, + options?: { preserveOriginal?: object }, +): any { + let finalized = false; + function safeFinalize(status: "ok" | "error") { + if (finalized) return; + finalized = true; + try { + callbacks.finalize(status); + } catch (e) { + Logger.error("netra: finalize callback error", e); + } + } + + const instrumentedPromise = (async () => { + try { + const value = await promise; + if (isAsyncIterable(value)) { + return wrapAsyncIterable(value as any, callbacks); + } + try { + callbacks.onSuccess?.(value); + } catch (e) { + Logger.error("netra: onSuccess callback error", e); + } + safeFinalize("ok"); + return value; + } catch (error) { + try { + callbacks.onError(error); + } catch { + Logger.error("netra: onError callback error", error); + } + safeFinalize("error"); + throw error; + } + })(); + + if (!options?.preserveOriginal) { + return instrumentedPromise; + } + + const original = options.preserveOriginal; + return new Proxy(instrumentedPromise, { + get(target, prop, receiver) { + if (prop === "then" || prop === "catch" || prop === "finally") { + const value = Reflect.get(target, prop, receiver); + if (typeof value === "function") return value.bind(target); + return value; + } + const originalValue = (original as any)[prop]; + if (originalValue !== undefined) { + if (typeof originalValue === "function") + return originalValue.bind(original); + return originalValue; + } + const value = Reflect.get(target, prop, receiver); + if (typeof value === "function") return value.bind(target); + return value; + }, + }); +} + +/** + * Unified response dispatcher. Detects response type and delegates: + * - AsyncIterable -> wrapAsyncIterable + * - Promise -> wrapPromise (which handles Promise internally) + * - Sync value -> onSuccess + finalize immediately + */ +export function wrapResponse( + response: T, + callbacks: ResponseCallbacks, + options?: { preserveOriginal?: object }, +): T { + if (isAsyncIterable(response)) { + return wrapAsyncIterable(response as any, callbacks) as T; + } + + if (isPromise(response)) { + return wrapPromise(response as any, callbacks, options) as T; + } + + try { + callbacks.onSuccess?.(response); + } catch (e) { + Logger.error("netra: onSuccess callback error", e); + } + try { + callbacks.finalize("ok"); + } catch (e) { + Logger.error("netra: finalize callback error", e); + } + return response; +} diff --git a/src/utils/serialization.ts b/src/utils/serialization.ts new file mode 100644 index 0000000..c9054dc --- /dev/null +++ b/src/utils/serialization.ts @@ -0,0 +1,81 @@ +const ELLIPSIS = "..."; + +function truncate(s: string, maxLength: number): string { + if (s.length <= maxLength) return s; + if (maxLength <= ELLIPSIS.length) return s.slice(0, maxLength); + return s.slice(0, maxLength - ELLIPSIS.length) + ELLIPSIS; +} + +/** + * Circular-reference-safe JSON.stringify with optional length truncation. + * + * - Strings pass through as-is (only truncated if over maxLength) + * - Functions, symbols, bigints get descriptive placeholders + * - Circular references become "[Circular]" + * - Large class instances (>20 keys) become "[ClassName]" + * - Result is truncated to `maxLength` when provided + */ +export function safeStringify( + value: unknown, + maxLength?: number, +): string { + if (typeof value === "string") { + if (maxLength && value.length > maxLength) { + return truncate(value, maxLength); + } + return value; + } + + const seen = new WeakSet(); + let result: string; + try { + result = JSON.stringify(value, (_key, val) => { + if (typeof val === "function") + return `[Function: ${val.name || "anonymous"}]`; + if (typeof val === "symbol") return val.toString(); + if (typeof val === "bigint") return val.toString(); + if (val !== null && typeof val === "object") { + if (seen.has(val)) return "[Circular]"; + seen.add(val); + const name = val.constructor?.name; + if ( + name && + name !== "Object" && + name !== "Array" && + Object.keys(val).length > 20 + ) { + return `[${name}]`; + } + } + return val; + }) ?? String(value); + } catch { + result = + (value as any)?.constructor?.name + ? `[${(value as any).constructor.name}]` + : String(value); + } + + if (maxLength && result.length > maxLength) { + return truncate(result, maxLength); + } + return result; +} + +/** + * Convert any value to a string suitable for span attributes. + * Primitives use `String()`, objects use `safeStringify`. + */ +export function serializeValue( + value: unknown, + maxLength?: number, +): string { + if (value === null || value === undefined) return String(value); + const t = typeof value; + if (t === "string" || t === "number" || t === "boolean") { + const s = String(value); + if (maxLength && s.length > maxLength) return truncate(s, maxLength); + return s; + } + return safeStringify(value, maxLength); +} diff --git a/src/version.ts b/src/version.ts new file mode 100644 index 0000000..dff351e --- /dev/null +++ b/src/version.ts @@ -0,0 +1 @@ +export const SDK_VERSION = "1.4.0-dev"; From 16abe5f014219c798c502b579476bd9902380d1b Mon Sep 17 00:00:00 2001 From: Nithish-KV Date: Thu, 2 Jul 2026 22:05:31 +0530 Subject: [PATCH 2/5] chore: Update library version --- package-lock.json | 4 ++-- package.json | 2 +- src/version.ts | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/package-lock.json b/package-lock.json index aa7c856..7694185 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "netra-sdk", - "version": "1.4.0-dev", + "version": "1.4.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "netra-sdk", - "version": "1.4.0-dev", + "version": "1.4.0", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", diff --git a/package.json b/package.json index 4650bdb..a813f28 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "netra-sdk", - "version": "1.4.0-dev", + "version": "1.4.0", "description": "A comprehensive TypeScript/JavaScript SDK for AI application observability built on top of OpenTelemetry and Traceloop", "type": "module", "main": "./dist/index.cjs", diff --git a/src/version.ts b/src/version.ts index dff351e..4268add 100644 --- a/src/version.ts +++ b/src/version.ts @@ -1 +1 @@ -export const SDK_VERSION = "1.4.0-dev"; +export const SDK_VERSION = "1.4.0"; From eee94858617ed346136d145b1ce96c653941ade0 Mon Sep 17 00:00:00 2001 From: Akash Vijay Date: Mon, 6 Jul 2026 09:32:47 +0530 Subject: [PATCH 3/5] [NET-1300] fix: Add cache token details for claude models in OpenAI Agent instrumentation (#102) --- .../openai-agents/attributes.ts | 22 ++++++++++++++++++- src/instrumentation/openai-agents/types.ts | 8 ++++++- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/src/instrumentation/openai-agents/attributes.ts b/src/instrumentation/openai-agents/attributes.ts index 9ada504..151ac18 100644 --- a/src/instrumentation/openai-agents/attributes.ts +++ b/src/instrumentation/openai-agents/attributes.ts @@ -239,6 +239,23 @@ function setUsageAttributes( span.setAttribute(SpanAttributes.LLM_USAGE_REASONING_TOKENS, Number(details.reasoning_tokens)); } } + + if (usage.input_tokens_details) { + const inputDetails = usage.input_tokens_details; + if (inputDetails.cached_tokens !== undefined) { + span.setAttribute(SpanAttributes.LLM_USAGE_CACHE_READ_INPUT_TOKENS, Number(inputDetails.cached_tokens)); + } + if (inputDetails.cache_write_tokens !== undefined) { + span.setAttribute(SpanAttributes.LLM_USAGE_CACHE_CREATION_INPUT_TOKENS, Number(inputDetails.cache_write_tokens)); + } + } + + if (usage.output_tokens_details) { + const outputDetails = usage.output_tokens_details; + if (outputDetails.reasoning_tokens !== undefined) { + span.setAttribute(SpanAttributes.LLM_USAGE_REASONING_TOKENS, Number(outputDetails.reasoning_tokens)); + } + } } interface ResponseObject { @@ -252,7 +269,7 @@ interface ResponseObject { input_tokens?: number; output_tokens?: number; total_tokens?: number; - input_tokens_details?: { cached_tokens?: number }; + input_tokens_details?: { cached_tokens?: number; cache_write_tokens?: number }; output_tokens_details?: { reasoning_tokens?: number }; }; output?: Array<{ @@ -314,6 +331,9 @@ function setResponseObjectUsageAttributes( if (usage.input_tokens_details?.cached_tokens !== undefined) { span.setAttribute(SpanAttributes.LLM_USAGE_CACHE_READ_INPUT_TOKENS, usage.input_tokens_details.cached_tokens); } + if (usage.input_tokens_details?.cache_write_tokens !== undefined) { + span.setAttribute(SpanAttributes.LLM_USAGE_CACHE_CREATION_INPUT_TOKENS, usage.input_tokens_details.cache_write_tokens); + } if (usage.output_tokens_details?.reasoning_tokens !== undefined) { span.setAttribute(SpanAttributes.LLM_USAGE_REASONING_TOKENS, usage.output_tokens_details.reasoning_tokens); } diff --git a/src/instrumentation/openai-agents/types.ts b/src/instrumentation/openai-agents/types.ts index 77a4f80..2ca6844 100644 --- a/src/instrumentation/openai-agents/types.ts +++ b/src/instrumentation/openai-agents/types.ts @@ -23,7 +23,13 @@ export interface SpanData { output?: unknown; model?: string; model_config?: Record; - usage?: { input_tokens?: number; output_tokens?: number; details?: Record | null }; + usage?: { + input_tokens?: number; + output_tokens?: number; + details?: Record | null; + input_tokens_details?: { cached_tokens?: number; cache_write_tokens?: number } | null; + output_tokens_details?: { reasoning_tokens?: number } | null; + }; // HandoffSpanData to_agent?: string; from_agent?: string; From 13cf4965596efea7465bda666f2b32e561a24f7f Mon Sep 17 00:00:00 2001 From: Nithish-KV Date: Tue, 7 Jul 2026 18:02:08 +0530 Subject: [PATCH 4/5] [NET-1287] feat: Add support for google genai instrumentation (#103) --- package-lock.json | 8 +- package.json | 6 +- src/config.ts | 4 +- src/instrumentation/base-instrumentor.ts | 227 +++++ src/instrumentation/google-genai/index.ts | 305 ++---- src/instrumentation/google-genai/types.ts | 6 + src/instrumentation/google-genai/utils.ts | 934 ++++++++---------- src/instrumentation/google-genai/version.ts | 4 - src/instrumentation/google-genai/wrappers.ts | 459 ++++----- .../google-generative-ai/index.ts | 116 +++ .../google-generative-ai/utils.ts | 633 ++++++++++++ .../google-generative-ai/version.ts | 5 + .../google-generative-ai/wrappers.ts | 365 +++++++ src/instrumentation/index.ts | 43 +- src/instrumentation/span-attributes.ts | 2 + src/instrumentation/utils.ts | 12 +- .../instrumentation-span-processor.ts | 1 + src/version.ts | 2 +- 18 files changed, 2088 insertions(+), 1044 deletions(-) create mode 100644 src/instrumentation/base-instrumentor.ts create mode 100644 src/instrumentation/google-genai/types.ts create mode 100644 src/instrumentation/google-generative-ai/index.ts create mode 100644 src/instrumentation/google-generative-ai/utils.ts create mode 100644 src/instrumentation/google-generative-ai/version.ts create mode 100644 src/instrumentation/google-generative-ai/wrappers.ts diff --git a/package-lock.json b/package-lock.json index 7694185..e5d293f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "netra-sdk", - "version": "1.4.0", + "version": "1.5.0", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "netra-sdk", - "version": "1.4.0", + "version": "1.5.0", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", @@ -35,6 +35,7 @@ }, "peerDependencies": { "@anthropic-ai/sdk": ">=0.60.0", + "@google/genai": ">=1.0.0", "@google/generative-ai": "^0.24.1", "@langchain/langgraph": "^1.1.1", "@langchain/ollama": "^1.2.1", @@ -52,6 +53,9 @@ "@anthropic-ai/sdk": { "optional": true }, + "@google/genai": { + "optional": true + }, "@google/generative-ai": { "optional": true }, diff --git a/package.json b/package.json index a813f28..c263922 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "netra-sdk", - "version": "1.4.0", + "version": "1.5.0", "description": "A comprehensive TypeScript/JavaScript SDK for AI application observability built on top of OpenTelemetry and Traceloop", "type": "module", "main": "./dist/index.cjs", @@ -67,6 +67,7 @@ "@langchain/ollama": "^1.2.1", "@mistralai/mistralai": ">=1.0.0", "@google/generative-ai": "^0.24.1", + "@google/genai": ">=1.0.0", "@opentelemetry/instrumentation": ">=0.53.0", "@opentelemetry/instrumentation-express": "^0.67.0", "@opentelemetry/instrumentation-http": "^0.219.0", @@ -105,6 +106,9 @@ "@google/generative-ai": { "optional": true }, + "@google/genai": { + "optional": true + }, "@anthropic-ai/sdk": { "optional": true }, diff --git a/src/config.ts b/src/config.ts index 43d0d13..9bf08b5 100644 --- a/src/config.ts +++ b/src/config.ts @@ -31,7 +31,8 @@ export enum NetraInstruments { // LLM Providers OPENAI = "openai", - GOOGLE_GENERATIVE_AI = "google_genai", + GOOGLE_GENAI = "google_genai", + GOOGLE_GENERATIVE_AI = "google_generative_ai", MISTRAL = "mistral_ai", GROQ = "groq", VERTEX_AI = "vertexai", @@ -70,6 +71,7 @@ export const DEFAULT_INSTRUMENTS_FOR_ROOT: Set = new Set([ NetraInstruments.ANTHROPIC, NetraInstruments.GROQ, NetraInstruments.MISTRAL, + NetraInstruments.GOOGLE_GENAI, NetraInstruments.GOOGLE_GENERATIVE_AI, NetraInstruments.VERTEX_AI, NetraInstruments.TOGETHER, diff --git a/src/instrumentation/base-instrumentor.ts b/src/instrumentation/base-instrumentor.ts new file mode 100644 index 0000000..117c5c1 --- /dev/null +++ b/src/instrumentation/base-instrumentor.ts @@ -0,0 +1,227 @@ +import { createRequire } from "module"; +import { trace, Tracer, TracerProvider } from "@opentelemetry/api"; +import { Logger } from "../logger"; + +export interface InstrumentorOptions { + tracerProvider?: TracerProvider; +} + +/** + * Shared lifecycle for Netra SDK instrumentors. + * + * Subclasses define three things: + * 1. extractClasses — pull patchable classes from a loaded module + * 2. applyPatches — wrap prototype methods + * 3. removePatches — unwrap (inverse of applyPatches) + * + * The base class owns: + * - ESM + CJS module resolution with dedup + * - Concurrency guard (single in-flight promise) + * - isInstrumented flag lifecycle + * - Tracer initialization + * - Consistent logging + */ +export abstract class BaseInstrumentor { + private _isInstrumented = false; + private _instrumentPromise: Promise | null = null; + private _resolvedClasses: TClasses[] = []; + private _generation = 0; + + protected _tracer: Tracer | null = null; + protected _tracerProvider?: TracerProvider; + + protected abstract readonly instrumentationName: string; + protected abstract readonly instrumentationVersion: string; + + /** + * The npm package name to resolve (used for ESM import and CJS require). + * Set to null to skip the default resolution and override resolveClasses(). + */ + protected abstract readonly packageName: string; + + /** + * Human-readable label for log messages (e.g. "Google GenAI"). + */ + protected abstract readonly displayName: string; + + /** + * Extract patchable classes from a loaded module. + * Return null if the module doesn't expose the expected API. + */ + protected abstract extractClasses(mod: any): TClasses | null; + + /** + * Apply instrumentation wrappers to one resolved class set. + * Return true if at least one method was successfully wrapped. + */ + protected abstract applyPatches(classes: TClasses, tracer: Tracer): boolean; + + /** + * Remove instrumentation wrappers (inverse of applyPatches). + */ + protected abstract removePatches(classes: TClasses): void; + + /** + * Check whether two resolved class sets refer to the same module load. + * Default: reference equality. Override for composite class objects. + */ + protected isSameClasses(a: TClasses, b: TClasses): boolean { + return a === b; + } + + /** + * Optional hook called during uninstrument() after prototype unwrapping. + * Use for extra cleanup (e.g. restoring patched instance methods). + */ + protected onUninstrument(): void {} + + get tracer(): Tracer | null { + return this._tracer; + } + + isInstrumented(): boolean { + return this._isInstrumented; + } + + get resolvedClasses(): ReadonlyArray { + return this._resolvedClasses; + } + + async instrument(options: InstrumentorOptions = {}): Promise { + if (this._isInstrumented) { + Logger.warn(`${this.displayName} is already instrumented`); + return this; + } + + if (this._instrumentPromise) { + return this._instrumentPromise; + } + + this._instrumentPromise = this._doInstrument(options); + try { + return await this._instrumentPromise; + } finally { + this._instrumentPromise = null; + } + } + + uninstrument(): void { + // Bump generation so any in-flight _doInstrument() will bail out + // after its async boundary instead of applying late patches. + this._generation++; + this._instrumentPromise = null; + + if (!this._isInstrumented) { + Logger.warn(`${this.displayName} is not instrumented`); + return; + } + + for (const classes of this._resolvedClasses) { + try { + this.removePatches(classes); + } catch (error) { + Logger.error(`${this.displayName}: failed to remove patches: ${error}`); + } + } + + try { + this.onUninstrument(); + } catch (error) { + Logger.error(`${this.displayName}: onUninstrument failed: ${error}`); + } finally { + this._resolvedClasses = []; + this._isInstrumented = false; + } + } + + private async _doInstrument(options: InstrumentorOptions): Promise { + const gen = this._generation; + + const classSets = await this.resolveClasses(); + if (classSets.length === 0) { + return this; + } + + // Re-check after the async boundary: abort if already instrumented + // or if uninstrument() was called while we were resolving. + if (this._isInstrumented || this._generation !== gen) { + return this; + } + + try { + this._tracerProvider = options.tracerProvider; + this._tracer = this._tracerProvider + ? this._tracerProvider.getTracer( + this.instrumentationName, + this.instrumentationVersion, + ) + : trace.getTracer( + this.instrumentationName, + this.instrumentationVersion, + ); + } catch (error) { + Logger.error(`${this.displayName}: failed to initialize tracer: ${error}`); + return this; + } + + let anyWrapped = false; + for (const classes of classSets) { + try { + if (this.applyPatches(classes, this._tracer)) { + anyWrapped = true; + } + } catch (error) { + Logger.error(`${this.displayName}: patch failed: ${error}`); + try { + this.removePatches(classes); + } catch { + Logger.error(`${this.displayName}: failed to remove patches: ${error}`); + } + } + } + + if (anyWrapped) { + this._isInstrumented = true; + } + return this; + } + + /** + * Resolve the target package via ESM import() and CJS createRequire(). + * Override this for non-standard resolution strategies. + */ + protected async resolveClasses(): Promise { + if (this._resolvedClasses.length > 0) return this._resolvedClasses; + + // ESM + try { + // @ts-ignore — peer dependency may not be installed + const mod = await import(this.packageName); + const classes = this.extractClasses(mod); + if (classes) { + this._resolvedClasses.push(classes); + } + } catch { + Logger.debug(`${this.displayName}: ESM import not available`); + } + + // CJS + try { + const req = createRequire(import.meta.url); + const mod = req(this.packageName); + const classes = this.extractClasses(mod); + if (classes) { + const isDuplicate = this._resolvedClasses.some((existing) => + this.isSameClasses(existing, classes), + ); + if (!isDuplicate) { + this._resolvedClasses.push(classes); + } + } + } catch { + Logger.debug(`${this.displayName}: CJS require not available`); + } + + return this._resolvedClasses; + } +} diff --git a/src/instrumentation/google-genai/index.ts b/src/instrumentation/google-genai/index.ts index 4350d11..3fa3755 100644 --- a/src/instrumentation/google-genai/index.ts +++ b/src/instrumentation/google-genai/index.ts @@ -1,258 +1,103 @@ /** - * Custom Google GenAI instrumentor for Netra SDK + * Google GenAI instrumentor for Netra SDK. + * + * The @google/genai SDK defines public Models methods (generateContent, etc.) + * as instance arrow functions that delegate to *Internal prototype methods. + * We patch the Internal methods on Models.prototype and the public methods + * on Chat.prototype to produce OTel spans. */ -import { createRequire } from "module"; -import { trace, Tracer, TracerProvider } from "@opentelemetry/api"; -import { Logger } from "../../logger"; -import { __version__ } from "./version"; -import { chatStreamWrapper, chatWrapper, embeddingsWrapper, startChatWrapper } from "./wrappers"; +import { Tracer } from "@opentelemetry/api"; import shimmer from "shimmer"; - -const INSTRUMENTATION_NAME = "netra.instrumentation.google_genai"; -const INSTRUMENTS = ["@google/genai >= 0.24.1"]; - -// Track instrumentation state -let isInstrumented = false; -let generativeModelClasses: any[] = []; - -export interface InstrumentorOptions { - tracerProvider?: TracerProvider; -} - -/** - * Resolve the Google GenAI module from the application's context. - * Tries ESM dynamic import first, then falls back to CJS require so the - * instrumentor works in both ESM and CommonJS projects. - */ -async function resolveGoogleGenerativeAIAsync(): Promise { - if (generativeModelClasses.length > 0) return generativeModelClasses; - - try { - // @ts-ignore - @google/generative-ai is an optional peer dependency - const googleGenAIModule = await import("@google/generative-ai"); - const esmClass = - googleGenAIModule.GenerativeModel || - googleGenAIModule.default?.GenerativeModel || - googleGenAIModule.default || - googleGenAIModule; - generativeModelClasses.push(esmClass); - } catch { - Logger.warn("Failed to resolve Google GenAI ESM module"); - } - - try { - const req = createRequire(import.meta.url); - const mod = req("@google/generative-ai"); - const cjsClass = - mod.GenerativeModel || - mod.default?.GenerativeModel || - mod.default || - mod; - if (!generativeModelClasses.includes(cjsClass)) { - generativeModelClasses.push(cjsClass); - } - } catch { - Logger.warn("Failed to resolve Google GenAI CJS module"); - } - - return generativeModelClasses; -} - -/** - * Synchronous version that returns cached classes. - * Must call resolveGoogleGenerativeAIAsync() first to populate cache. - */ -function resolveGoogleGenerativeAI(): any[] { - return generativeModelClasses; +import { Logger } from "../../logger"; +import { BaseInstrumentor } from "../base-instrumentor"; +import { __version__ } from "./version"; +import { + chatStreamWrapper, + chatWrapper, + embeddingsWrapper, +} from "./wrappers"; + +interface GoogleGenAIClasses { + Models: any; + Chat?: any; } -/** - * Custom Google GenAI instrumentor for Netra SDK - */ -export class NetraGoogleGenerativeAIInstrumentor { - private tracer: Tracer | null = null; - private tracerProvider?: TracerProvider; +export class NetraGoogleGenAIInstrumentor extends BaseInstrumentor { + protected readonly instrumentationName = "netra.instrumentation.google_genai"; + protected readonly instrumentationVersion = __version__; + protected readonly packageName = "@google/genai"; + protected readonly displayName = "Google GenAI"; - constructor() { - // Tracer is initialized lazily during instrument() + protected extractClasses(mod: any): GoogleGenAIClasses | null { + const root = mod.default ?? mod; + if (!root.Models) return null; + return { Models: root.Models, Chat: root.Chat }; } - /** - * Returns the list of instrumentation dependencies - */ - instrumentationDependencies(): string[] { - return [...INSTRUMENTS]; + protected isSameClasses(a: GoogleGenAIClasses, b: GoogleGenAIClasses): boolean { + return a.Models === b.Models; } - /** - * Instrument Google GenAI client methods (async version) - * Tries both ESM and CJS resolution to cover dual-package setups. - */ - async instrumentAsync( - options: InstrumentorOptions = {}, - ): Promise { - if (isInstrumented) { - Logger.warn("Google GenAI is already instrumented"); - return this; - } - - const classes = await resolveGoogleGenerativeAIAsync(); - if (classes.length === 0) { - return this; + protected applyPatches(classes: GoogleGenAIClasses, tracer: Tracer): boolean { + const modelsProto = classes.Models?.prototype; + if (!modelsProto) { + Logger.error("Google GenAI: Models.prototype not found"); + return false; } - try { - this.tracerProvider = options.tracerProvider; - this.tracer = this.tracerProvider - ? this.tracerProvider.getTracer(INSTRUMENTATION_NAME, __version__) - : trace.getTracer(INSTRUMENTATION_NAME, __version__); - } catch (error) { - Logger.error(`Failed to initialize tracer: ${error}`); - return this; - } - - classes.forEach((model) => this._instrumentGenerativeModel(model)); - - isInstrumented = true; - return this; - } - - /** - * Instrument Google GenAI client methods (sync version) - */ - instrument( - options: InstrumentorOptions = {}, - ): NetraGoogleGenerativeAIInstrumentor { - if (isInstrumented) { - Logger.warn("Google GenAI is already instrumented"); - return this; - } + let wrapped = false; - const classes = resolveGoogleGenerativeAI(); - if (classes.length === 0) { - this.instrumentAsync(options).catch((e) => { - Logger.error("Failed to instrument Google GenAI:", e); - }); - return this; + // Public methods are instance arrow functions set in the constructor, + // so shimmer cannot wrap them on the prototype. They delegate to + // *Internal prototype methods which ARE on the prototype. + if (typeof modelsProto.generateContentInternal === "function") { + shimmer.wrap(modelsProto, "generateContentInternal", chatWrapper(tracer)); + wrapped = true; } - - try { - this.tracerProvider = options.tracerProvider; - this.tracer = this.tracerProvider - ? this.tracerProvider.getTracer(INSTRUMENTATION_NAME, __version__) - : trace.getTracer(INSTRUMENTATION_NAME, __version__); - } catch (error) { - Logger.error(`Failed to initialize tracer: ${error}`); - return this; + if (typeof modelsProto.generateContentStreamInternal === "function") { + shimmer.wrap(modelsProto, "generateContentStreamInternal", chatStreamWrapper(tracer)); + wrapped = true; } - - classes.forEach((model) => this._instrumentGenerativeModel(model)); - - isInstrumented = true; - return this; - } - - /** - * Uninstrument Google GenAI client methods - */ - uninstrument(): void { - if (!isInstrumented) { - Logger.warn("Google GenAI is not instrumented"); - return; + if (typeof modelsProto.embedContentInternal === "function") { + shimmer.wrap(modelsProto, "embedContentInternal", embeddingsWrapper(tracer)); + wrapped = true; } - const classes = resolveGoogleGenerativeAI(); - classes.forEach((model) => this._uninstrumentGenerativeModel(model)); - - generativeModelClasses = []; - isInstrumented = false; - } - - /** - * Check if Google GenAI is currently instrumented - */ - isInstrumented(): boolean { - return isInstrumented; - } - - private _instrumentGenerativeModel(GenerativeModel: any): void { - if (!this.tracer) return; - - try { - if (!GenerativeModel?.prototype) { - Logger.error( - "Failed to find Google GenAI GenerativeModel to instrument", - ); - return; + const chatProto = classes.Chat?.prototype; + if (chatProto) { + if (typeof chatProto.sendMessage === "function") { + shimmer.wrap(chatProto, "sendMessage", chatWrapper(tracer)); + wrapped = true; } - - const tracer = this.tracer; - - shimmer.wrap( - GenerativeModel.prototype, - "generateContent", - chatWrapper(tracer), - ); - - shimmer.wrap( - GenerativeModel.prototype, - "generateContentStream", - chatStreamWrapper(tracer), - ); - - shimmer.wrap( - GenerativeModel.prototype, - "embedContent", - embeddingsWrapper(tracer), - ); - - if (typeof GenerativeModel.prototype.startChat === "function") { - shimmer.wrap( - GenerativeModel.prototype, - "startChat", - startChatWrapper(tracer), - ); + if (typeof chatProto.sendMessageStream === "function") { + shimmer.wrap(chatProto, "sendMessageStream", chatStreamWrapper(tracer)); + wrapped = true; } - } catch (error) { - Logger.debug( - `Google GenAI instrumentation: failed to instrument: ${error}`, - ); } + + return wrapped; } - private _uninstrumentGenerativeModel(GenerativeModel: any): void { - try { - if (!GenerativeModel?.prototype) return; + protected removePatches(classes: GoogleGenAIClasses): void { + const modelsProto = classes.Models?.prototype; + if (modelsProto) { + if (typeof modelsProto.generateContentInternal === "function") + shimmer.unwrap(modelsProto, "generateContentInternal"); + if (typeof modelsProto.generateContentStreamInternal === "function") + shimmer.unwrap(modelsProto, "generateContentStreamInternal"); + if (typeof modelsProto.embedContentInternal === "function") + shimmer.unwrap(modelsProto, "embedContentInternal"); + } - if (typeof GenerativeModel.prototype.generateContent === "function") { - shimmer.unwrap(GenerativeModel.prototype, "generateContent"); - } - if ( - typeof GenerativeModel.prototype.generateContentStream === "function" - ) { - shimmer.unwrap(GenerativeModel.prototype, "generateContentStream"); - } - if (typeof GenerativeModel.prototype.embedContent === "function") { - shimmer.unwrap(GenerativeModel.prototype, "embedContent"); - } - if (typeof GenerativeModel.prototype.startChat === "function") { - shimmer.unwrap(GenerativeModel.prototype, "startChat"); - } - } catch (error) { - Logger.debug(`Failed to uninstrument Google GenAI: ${error}`); + const chatProto = classes.Chat?.prototype; + if (chatProto) { + if (typeof chatProto.sendMessage === "function") + shimmer.unwrap(chatProto, "sendMessage"); + if (typeof chatProto.sendMessageStream === "function") + shimmer.unwrap(chatProto, "sendMessageStream"); } } } -// Export singleton instance for convenience -export const googleGenerativeAIInstrumentor = - new NetraGoogleGenerativeAIInstrumentor(); - -// Re-export wrappers for advanced usage -export { chatWrapper, chatStreamWrapper, embeddingsWrapper, startChatWrapper } from "./wrappers"; - -// Re-export utilities -export { setRequestAttributes, setResponseAttributes } from "./utils"; - -export { __version__ } from "./version"; +export const googleGenAIInstrumentor = new NetraGoogleGenAIInstrumentor(); diff --git a/src/instrumentation/google-genai/types.ts b/src/instrumentation/google-genai/types.ts new file mode 100644 index 0000000..407353d --- /dev/null +++ b/src/instrumentation/google-genai/types.ts @@ -0,0 +1,6 @@ +export type GoogleGenAIRequestType = "chat" | "embedding"; + +export const SPAN_NAMES = { + CHAT: "google_genai.chat", + EMBEDDING: "google_genai.embedding", +} as const; diff --git a/src/instrumentation/google-genai/utils.ts b/src/instrumentation/google-genai/utils.ts index be4b124..6b43e29 100644 --- a/src/instrumentation/google-genai/utils.ts +++ b/src/instrumentation/google-genai/utils.ts @@ -1,640 +1,568 @@ /** - * Utility functions for Google GenAI instrumentation + * Provider-specific utilities for @google/genai instrumentation. * - * Google GenAI has a different response format than OpenAI: - * - Response: { response: EnhancedGenerateContentResponse } - * - EnhancedGenerateContentResponse: { candidates, usageMetadata, promptFeedback } - * - UsageMetadata: { promptTokenCount, candidatesTokenCount, totalTokenCount, cachedContentTokenCount } + * The @google/genai SDK uses a different request/response shape from OpenAI: + * Request: { model, contents, config: { temperature, topP, ... } } + * Response: GenerateContentResponse with usageMetadata, candidates[], text accessor + * Embed: EmbedContentResponse with embeddings[] + * + * Because these shapes differ from OpenAI's flat kwargs and usage.prompt_tokens + * convention, we do custom mapping here rather than delegating fully to the + * shared setBaseRequestAttributes / setBaseResponseAttributes. */ import { Span } from "@opentelemetry/api"; +import { Config } from "../../config"; +import { Logger } from "../../logger"; +import { safeStringify } from "../../utils/serialization"; import { SpanAttributes } from "../span-attributes"; -import * as dotenv from "dotenv"; - -dotenv.config(); +import { + TracedMessage, + hasContent, + isDict, + isTraceContentEnabled, + writeCompletionAttributes, + writePromptAttributes, +} from "../utils"; -function safeStringify(value: unknown): string { - try { - if (typeof value === "string") return value; - return JSON.stringify(value); - } catch { - return String(value); - } -} +const LOG_PREFIX = "netra.instrumentation.google_genai"; /** - * Extract the model name from the model string. - * @param model - The model string. - * @returns The model name without the "models/" prefix if it exists. - */ -export function extractModelName(model: string): string { - if (model && model.startsWith("models/")) { - return model.replace(/^models\//, ""); - } - return model; -} - -/** - * Normalize role values from Google GenAI. + * Flatten @google/genai params into the kwargs shape expected by the shared + * PARAM_ATTRIBUTE_MAP, then set provider-specific extras. * - * Google GenAI uses "model" to indicate the assistant role. - * This function maps "model" → "assistant" and returns any other role unchanged in lowercase. + * @param params - The raw GenerateContentParameters / EmbedContentParameters + * object the user passed to the SDK method. */ -function normalizeGenAIRole(raw: string): string { - const rawLower = raw.toLowerCase(); - return rawLower === "model" ? "assistant" : rawLower; -} - export function setRequestAttributes( span: Span, - kwargs: Record, + params: Record, requestType: string, - args: Record, ): void { - // Use a private property on the span to store kwargs temporarily for setResponseAttributes - (span as any)._netra_kwargs = kwargs; - if (!span.isRecording()) { - return; - } - - span.setAttribute(SpanAttributes.LLM_REQUEST_TYPE, requestType); - span.setAttribute(SpanAttributes.LLM_SYSTEM, "google_genai"); - - // Model is set on the GenerativeModel instance, not in the request kwargs - // We need to access it from `this.model` in the wrapper if available - // For now, set from kwargs if provided - if (kwargs.model !== undefined) { - span.setAttribute(SpanAttributes.LLM_REQUEST_MODEL, String(kwargs.model)); - } - - // Generation config parameters (from generationConfig object or direct kwargs) - const generationConfig = - (kwargs.generationConfig as Record) ?? kwargs; - - if (generationConfig.temperature !== undefined) { - span.setAttribute( - SpanAttributes.LLM_REQUEST_TEMPERATURE, - Number(generationConfig.temperature), - ); - } - - if (generationConfig.topP !== undefined) { - span.setAttribute( - SpanAttributes.LLM_REQUEST_TOP_P, - Number(generationConfig.topP), - ); - } - - if (generationConfig.topK !== undefined) { - span.setAttribute("gen_ai.request.top_k", Number(generationConfig.topK)); - } + try { + if (!span.isRecording()) return; - if (generationConfig.maxOutputTokens !== undefined) { - span.setAttribute( - SpanAttributes.LLM_REQUEST_MAX_TOKENS, - Number(generationConfig.maxOutputTokens), - ); - } + span.setAttribute(SpanAttributes.LLM_REQUEST_TYPE, requestType); + span.setAttribute(SpanAttributes.LLM_SYSTEM, "google_genai"); - if (generationConfig.stopSequences !== undefined) { - span.setAttribute( - SpanAttributes.LLM_CHAT_STOP_SEQUENCES, - safeStringify(generationConfig.stopSequences), - ); - } + if (params.model) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_MODEL, + extractModelName(String(params.model)), + ); + } - // Candidate count - if (generationConfig.candidateCount !== undefined) { - span.setAttribute( - "gen_ai.request.candidate_count", - Number(generationConfig.candidateCount), - ); - } + const cfg = (params.config ?? {}) as Record; - // Presence/frequency penalty - if (generationConfig.presencePenalty !== undefined) { - span.setAttribute( - SpanAttributes.LLM_PRESENCE_PENALTY, - Number(generationConfig.presencePenalty), - ); - } - if (generationConfig.frequencyPenalty !== undefined) { - span.setAttribute( - SpanAttributes.LLM_FREQUENCY_PENALTY, - Number(generationConfig.frequencyPenalty), - ); - } + if (cfg.temperature !== undefined) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_TEMPERATURE, + Number(cfg.temperature), + ); + } + if (cfg.topP !== undefined) { + span.setAttribute(SpanAttributes.LLM_REQUEST_TOP_P, Number(cfg.topP)); + } + if (cfg.topK !== undefined) { + span.setAttribute(SpanAttributes.LLM_REQUEST_TOP_K, Number(cfg.topK)); + } + if (cfg.maxOutputTokens !== undefined) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_MAX_TOKENS, + Number(cfg.maxOutputTokens), + ); + } + if (cfg.frequencyPenalty !== undefined) { + span.setAttribute( + SpanAttributes.LLM_FREQUENCY_PENALTY, + Number(cfg.frequencyPenalty), + ); + } + if (cfg.presencePenalty !== undefined) { + span.setAttribute( + SpanAttributes.LLM_PRESENCE_PENALTY, + Number(cfg.presencePenalty), + ); + } + if (cfg.stopSequences !== undefined) { + span.setAttribute( + SpanAttributes.LLM_CHAT_STOP_SEQUENCES, + safeStringify(cfg.stopSequences), + ); + } - // Embedding dimensions - if (kwargs.dimensions !== undefined) { - span.setAttribute("gen_ai.request.dimensions", Number(kwargs.dimensions)); + if (isTraceContentEnabled()) { + const messages = buildGoogleInputMessages(params, cfg); + writePromptAttributes(span, messages); + } + } catch (e) { + Logger.error(`${LOG_PREFIX}: setRequestAttributes error`, e); } +} - // Tools - if (Array.isArray(kwargs.tools) && kwargs.tools.length > 0) { - span.setAttribute("gen_ai.request.tools_count", kwargs.tools.length); - } +/** + * Strips common prefix patterns from Google model identifiers. + * "models/gemini-2.0-flash" -> "gemini-2.0-flash" + */ +function extractModelName(model: string): string { + const MODEL_PREFIX = "models/"; + const TUNED_MODELS_PREFIX = "tunedModels/"; + const PUBLISHERS_PREFIX = "publishers/"; + const PROJECTS_PREFIX = "projects/"; + const MODELS_SEGMENT = "/models/"; - // Tool config - if (kwargs.toolConfig !== undefined) { - span.setAttribute( - "gen_ai.request.tool_config", - safeStringify(kwargs.toolConfig), - ); - } + if (model.startsWith(MODEL_PREFIX)) return model.slice(MODEL_PREFIX.length); - // Safety settings - if ( - Array.isArray(kwargs.safetySettings) && - kwargs.safetySettings.length > 0 - ) { - span.setAttribute( - "gen_ai.request.safety_settings_count", - kwargs.safetySettings.length, - ); - } + if (model.startsWith(TUNED_MODELS_PREFIX)) return model; - // System instruction - if (kwargs.systemInstruction !== undefined) { - if (isTraceContentEnabled()) { - span.setAttribute( - "gen_ai.request.system_instruction", - safeStringify(kwargs.systemInstruction), - ); - } - span.setAttribute("gen_ai.request.has_system_instruction", true); + const publisherIdx = model.indexOf(PUBLISHERS_PREFIX); + if (publisherIdx !== -1) { + const modelsIdx = model.indexOf(MODELS_SEGMENT, publisherIdx); + if (modelsIdx !== -1) return model.slice(modelsIdx + MODELS_SEGMENT.length); } - // Content tracing - prompts - if (isTraceContentEnabled()) { - _setPromptAttributes(span, kwargs, args); + const slashIdx = model.indexOf("/"); + if (slashIdx !== -1 && !model.startsWith(PROJECTS_PREFIX)) { + return model.slice(slashIdx + 1); } -} -function isTraceContentEnabled(): boolean { - const raw = - process.env.TRACELOOP_TRACE_CONTENT ?? - process.env.NETRA_TRACE_CONTENT ?? - ""; - return ["1", "true"].includes(String(raw).toLowerCase()); + return model; } /** - * Extract and set prompt content from Google GenAI request + * Build TracedMessage[] from @google/genai request params. + * + * `contents` can be: string, Part, Part[], Content, Content[] + * Each Content has { role, parts: Part[] }, each Part has { text? } or other fields. */ -function _setPromptAttributes( - span: Span, - kwargs: Record, - args: any, -): void { - // For generateContent, the prompt can be: - // 1. A string (simple prompt) - // 2. An array of Parts (Array) - // 3. A GenerateContentRequest object with contents array - - let promptIndex = 0; - - // 1. Add system instruction if present (from getGenerativeModel) - if (kwargs.systemInstruction !== undefined) { - const systemInstruction = kwargs.systemInstruction as any; - let systemContent = ""; - - if (typeof systemInstruction === "string") { - systemContent = systemInstruction; - } else if ( - systemInstruction.parts && - Array.isArray(systemInstruction.parts) - ) { - systemContent = systemInstruction.parts - .filter((p: any) => p.text !== undefined) - .map((p: any) => String(p.text)) - .join(""); - } else if (systemInstruction.text) { - systemContent = String(systemInstruction.text); - } else { - systemContent = JSON.stringify(systemInstruction); - } +function buildGoogleInputMessages( + params: Record, + cfg: Record, +): TracedMessage[] { + const messages: TracedMessage[] = []; - if (systemContent) { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, - "system", - ); - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - systemContent, - ); - promptIndex++; - } - } - - // 2. Chat history from startChat (multiturn context) - if (kwargs.history && Array.isArray(kwargs.history)) { - for (const turn of kwargs.history as Array>) { - const role = normalizeGenAIRole(String(turn.role ?? "user")); - const parts = turn.parts as Array> | undefined; + // System instruction + if (hasContent(cfg.systemInstruction)) { + const sysContent = + typeof cfg.systemInstruction === "string" + ? cfg.systemInstruction + : safeStringify(cfg.systemInstruction, Config.CONVERSATION_MAX_LEN); + messages.push({ role: "system", content: sysContent }); + } + + // Multi-turn chat history (injected by the wrapper from Chat instance) + const history = params._history as Array> | undefined; + if (Array.isArray(history)) { + for (const turn of history) { + const role = normalizeRole(String(turn.role ?? "user")); + const parts = turn.parts as unknown[] | undefined; if (Array.isArray(parts)) { - const textContent = parts - .filter((p) => p.text !== undefined) - .map((p) => String(p.text)) - .join(""); - if (textContent) { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, - role, - ); - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - textContent, - ); - promptIndex++; - } + const text = extractTextFromParts(parts); + if (text) messages.push({ role, content: text }); } } } - // 3. Add prompts from args (generateContent/embedContent call) - if (!args) return; + const contents = params.contents ?? params.message; + if (!hasContent(contents)) return messages; - // Handle string prompt - if (typeof args === "string") { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, - "user", - ); - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - args, - ); - promptIndex++; - return; + if (typeof contents === "string") { + messages.push({ role: "user", content: contents }); + return messages; } - // Handle Array - if (Array.isArray(args)) { - const textParts = args - .map((p: any) => { - if (typeof p === "string") return p; - if (p && typeof p.text === "string") return p.text; - return ""; - }) - .filter(Boolean) - .join(" "); - - if (textParts) { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, - "user", - ); - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - textParts, - ); - promptIndex++; - } - return; - } - - // Handle GenerateContentRequest object { contents: [...] } - const contents = args.contents as Array> | undefined; if (Array.isArray(contents)) { - for (const content of contents) { - const role = String(content.role ?? "user"); - const parts = content.parts as Array> | undefined; - - if (Array.isArray(parts)) { - const textParts = parts - .filter((p) => p.text !== undefined) - .map((p) => String(p.text)) - .join(""); - - if (textParts) { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, - role, - ); - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - textParts, - ); - promptIndex++; - } - - // Track non-text parts - const inlineDataParts = parts.filter((p) => p.inlineData !== undefined); - if (inlineDataParts.length > 0) { - span.setAttribute( - `gen_ai.prompt.${promptIndex - 1}.has_inline_data`, - true, - ); - span.setAttribute( - `gen_ai.prompt.${promptIndex - 1}.inline_data_count`, - inlineDataParts.length, - ); - } + for (const item of contents) { + if (typeof item === "string") { + messages.push({ role: "user", content: item }); + } else if (isDict(item) && item.role && Array.isArray(item.parts)) { + // Content object: { role, parts } + const role = normalizeRole(String(item.role)); + const text = extractTextFromParts(item.parts as unknown[]); + if (text) messages.push({ role, content: text }); + } else if (isDict(item) && item.text !== undefined) { + // Bare Part with text + messages.push({ role: "user", content: String(item.text) }); + } else { + messages.push({ + role: "user", + content: safeStringify(item, Config.CONVERSATION_MAX_LEN), + }); } } - } + } else if (isDict(contents) && Array.isArray((contents as any).parts)) { + // Single Content object + const role = normalizeRole(String((contents as any).role ?? "user")); + const text = extractTextFromParts((contents as any).parts as unknown[]); + if (text) messages.push({ role, content: text }); + } else if (isDict(contents) && (contents as any).text !== undefined) { + // Single Part object with text + messages.push({ role: "user", content: String((contents as any).text) }); + } else { + messages.push({ + role: "user", + content: safeStringify(contents, Config.CONVERSATION_MAX_LEN), + }); + } + + return messages; +} - // For embedContent, handle content object { parts: [...] } or string - if (args.content !== undefined) { - const content = args.content as Record | string; - if (typeof content === "string") { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - content, +function normalizeRole(role: string): string { + if (role === "model") return "assistant"; + return role; +} + +function extractTextFromParts(parts: unknown[]): string { + const texts: string[] = []; + for (const part of parts) { + if (!isDict(part)) continue; + if (typeof part.text === "string") { + texts.push(part.text); + } else if (part.functionCall) { + texts.push(safeStringify(part.functionCall, Config.CONVERSATION_MAX_LEN)); + } else if (part.functionResponse) { + texts.push( + safeStringify(part.functionResponse, Config.CONVERSATION_MAX_LEN), ); - promptIndex++; - } else if (content.parts !== undefined) { - const parts = content.parts as Array>; - const textContent = parts - .filter((p) => p.text !== undefined) - .map((p) => String(p.text)) - .join(""); - if (textContent) { - span.setAttribute( - `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, - textContent, - ); - promptIndex++; - } } } + return texts.join(""); } /** - * Set response attributes for Google GenAI responses - * Handles the specific structure of GenerateContentResult + * Extract and set span attributes from a GenerateContentResponse or + * EmbedContentResponse. + * + * GenerateContentResponse: + * { responseId, modelVersion, candidates, usageMetadata, text, functionCalls } + * + * EmbedContentResponse: + * { embeddings: ContentEmbedding[] } */ export function setResponseAttributes( span: Span, response: Record, ): void { - if (!span.isRecording()) { - return; - } - - // Google GenAI returns { response: EnhancedGenerateContentResponse } - // The response object itself is what we need to parse - const actualResponse = - (response.response as Record) ?? response; - - // Set usage metadata - _setUsageAttributes(span, actualResponse); + try { + if (!span.isRecording()) return; - // Set candidate attributes - _setCandidateAttributes(span, actualResponse); + if (response.responseId) { + span.setAttribute("llm.response.id", String(response.responseId)); + } + if (response.modelVersion) { + span.setAttribute( + SpanAttributes.LLM_RESPONSE_MODEL, + String(response.modelVersion), + ); + } - // Set prompt feedback if present (content filtering) - _setPromptFeedbackAttributes(span, actualResponse); + setUsageAttributes(span, response); + setFinishReason(span, response); + setEmbeddingMeta(span, response); - // Set completion content if tracing is enabled - if (isTraceContentEnabled()) { - _setCompletionAttributes(span, actualResponse); + if (isTraceContentEnabled()) { + const messages = buildGoogleOutputMessages(response); + writeCompletionAttributes(span, messages); + } + } catch (e) { + Logger.error(`${LOG_PREFIX}: setResponseAttributes error`, e); } - - // Handle embedding response - _setEmbeddingResponseAttributes(span, actualResponse); } /** - * Extract and set token usage from usageMetadata + * Map @google/genai usageMetadata to OTel GenAI token attributes. + * + * UsageMetadata fields: promptTokenCount, candidatesTokenCount, + * totalTokenCount, cachedContentTokenCount, thoughtsTokenCount */ -function _setUsageAttributes( +function setUsageAttributes( span: Span, response: Record, ): void { - const usageMetadata = response.usageMetadata as - | Record - | undefined; - if (!usageMetadata) return; + const usage = response.usageMetadata as Record | undefined; + if (!usage) return; - // Prompt tokens - if (usageMetadata.promptTokenCount !== undefined) { + if (usage.promptTokenCount !== undefined) { span.setAttribute( SpanAttributes.LLM_USAGE_PROMPT_TOKENS, - Number(usageMetadata.promptTokenCount), + Number(usage.promptTokenCount), ); } - - // Completion/candidates tokens - if (usageMetadata.candidatesTokenCount !== undefined) { + if (usage.candidatesTokenCount !== undefined) { span.setAttribute( SpanAttributes.LLM_USAGE_COMPLETION_TOKENS, - Number(usageMetadata.candidatesTokenCount), + Number(usage.candidatesTokenCount), ); } - - // Total tokens - if (usageMetadata.totalTokenCount !== undefined) { + if (usage.totalTokenCount !== undefined) { span.setAttribute( SpanAttributes.LLM_USAGE_TOTAL_TOKENS, - Number(usageMetadata.totalTokenCount), + Number(usage.totalTokenCount), ); } - - // Cached content tokens - if (usageMetadata.cachedContentTokenCount !== undefined) { + if (usage.cachedContentTokenCount !== undefined) { span.setAttribute( SpanAttributes.LLM_USAGE_CACHE_READ_INPUT_TOKENS, - Number(usageMetadata.cachedContentTokenCount), + Number(usage.cachedContentTokenCount), + ); + } + if (usage.thoughtsTokenCount !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_REASONING_TOKENS, + Number(usage.thoughtsTokenCount), ); } } -/** - * Extract and set attributes from candidates - */ -function _setCandidateAttributes( - span: Span, - response: Record, -): void { +function setFinishReason(span: Span, response: Record): void { const candidates = response.candidates as | Array> | undefined; if (!Array.isArray(candidates) || candidates.length === 0) return; - span.setAttribute("gen_ai.response.candidate_count", candidates.length); - - const firstCandidate = candidates[0]; - - // Finish reason - if (firstCandidate.finishReason !== undefined) { + const reason = candidates[0].finishReason; + if (reason) { span.setAttribute( - "gen_ai.response.finish_reason", - String(firstCandidate.finishReason), + SpanAttributes.LLM_RESPONSE_FINISH_REASON, + String(reason), ); + span.setAttribute("gen_ai.response.finish_reason", String(reason)); } +} - // Average log probs (if present) - if (firstCandidate.avgLogprobs !== undefined) { - span.setAttribute( - "gen_ai.response.avg_logprobs", - Number(firstCandidate.avgLogprobs), - ); +function setEmbeddingMeta(span: Span, response: Record): void { + // Single embedding response + const singleEmbed = response.embedding as Record | undefined; + if (singleEmbed?.values !== undefined) { + const values = singleEmbed.values as number[]; + span.setAttribute("gen_ai.response.embedding_dimensions", values.length); + + const stats = singleEmbed.statistics as Record | undefined; + if (stats?.tokenCount !== undefined) { + const tokenCount = Number(stats.tokenCount); + span.setAttribute(SpanAttributes.LLM_USAGE_PROMPT_TOKENS, tokenCount); + span.setAttribute(SpanAttributes.LLM_USAGE_TOTAL_TOKENS, tokenCount); + } + return; } - // Safety ratings - const safetyRatings = firstCandidate.safetyRatings as + // Batch embedding response + const embeddings = response.embeddings as | Array> | undefined; - if (Array.isArray(safetyRatings) && safetyRatings.length > 0) { - span.setAttribute( - "gen_ai.response.safety_ratings_count", - safetyRatings.length, - ); + if (!Array.isArray(embeddings) || embeddings.length === 0) return; - // Set individual safety ratings - for (let i = 0; i < safetyRatings.length; i++) { - const rating = safetyRatings[i]; - if (rating.category !== undefined) { - span.setAttribute( - `gen_ai.response.safety_rating.${i}.category`, - String(rating.category), - ); - } - if (rating.probability !== undefined) { - span.setAttribute( - `gen_ai.response.safety_rating.${i}.probability`, - String(rating.probability), - ); - } - } - } + span.setAttribute("gen_ai.response.embedding_count", embeddings.length); - // Citation metadata - const citationMetadata = firstCandidate.citationMetadata as - | Record - | undefined; - if (citationMetadata?.citationSources !== undefined) { - const sources = citationMetadata.citationSources as Array; - span.setAttribute("gen_ai.response.citation_count", sources.length); + const first = embeddings[0]; + const values = first?.values as number[] | undefined; + if (Array.isArray(values)) { + span.setAttribute("gen_ai.response.embedding_dimensions", values.length); } - // Grounding metadata - if (firstCandidate.groundingMetadata !== undefined) { - span.setAttribute("gen_ai.response.has_grounding", true); + // Aggregate token counts across all embeddings in the batch + let totalTokens = 0; + let hasTokenCount = false; + for (const emb of embeddings) { + const stats = emb.statistics as Record | undefined; + if (stats?.tokenCount !== undefined) { + totalTokens += Number(stats.tokenCount); + hasTokenCount = true; + } + } + if (hasTokenCount) { + span.setAttribute(SpanAttributes.LLM_USAGE_PROMPT_TOKENS, totalTokens); + span.setAttribute(SpanAttributes.LLM_USAGE_TOTAL_TOKENS, totalTokens); } } /** - * Set prompt feedback attributes (content filtering info) + * Build TracedMessage[] from @google/genai response. + * Handles both text output and function calls. */ -function _setPromptFeedbackAttributes( - span: Span, +function buildGoogleOutputMessages( response: Record, -): void { - const promptFeedback = response.promptFeedback as - | Record - | undefined; - if (!promptFeedback) return; - - if (promptFeedback.blockReason !== undefined) { - span.setAttribute( - "gen_ai.response.prompt_block_reason", - String(promptFeedback.blockReason), - ); - } +): TracedMessage[] { + const messages: TracedMessage[] = []; - if (promptFeedback.blockReasonMessage !== undefined) { - span.setAttribute( - "gen_ai.response.prompt_block_message", - String(promptFeedback.blockReasonMessage), - ); + // text accessor (available on GenerateContentResponse) + const text = response.text; + if (typeof text === "string" && text.length > 0) { + messages.push({ role: "assistant", content: text }); } - const safetyRatings = promptFeedback.safetyRatings as + // Function calls + const functionCalls = response.functionCalls as | Array> | undefined; - if (Array.isArray(safetyRatings)) { - span.setAttribute( - "gen_ai.response.prompt_safety_ratings_count", - safetyRatings.length, - ); + if (Array.isArray(functionCalls)) { + for (const fc of functionCalls) { + messages.push({ + role: "tool", + content: safeStringify( + { name: fc.name, arguments: fc.args }, + Config.CONVERSATION_MAX_LEN, + ), + }); + } + } + + // If text accessor wasn't available, fall back to candidates + if (messages.length === 0) { + const candidates = response.candidates as + | Array> + | undefined; + if (Array.isArray(candidates)) { + for (const candidate of candidates) { + const content = candidate.content as + | Record + | undefined; + if (!content || !Array.isArray(content.parts)) continue; + for (const part of content.parts as Array>) { + if (typeof part.text === "string" && part.text.length > 0) { + messages.push({ role: "assistant", content: part.text }); + } + if (part.functionCall && isDict(part.functionCall)) { + const fc = part.functionCall as Record; + messages.push({ + role: "tool", + content: safeStringify( + { name: fc.name, arguments: fc.args }, + Config.CONVERSATION_MAX_LEN, + ), + }); + } + } + } + } } + + // Embedding responses: generate structured output for the Netra output field. + if (messages.length === 0) { + // Single embedding: { embedding: { values: [...] } } + const singleEmbed = response.embedding as + | Record + | undefined; + if (singleEmbed?.values !== undefined) { + const values = singleEmbed.values as number[]; + messages.push({ + role: "assistant", + content: safeStringify({ + dimensions: values.length, + preview: values.slice(0, 5), + }), + }); + } + + // Batch embeddings: { embeddings: [ { values: [...] }, ... ] } + const embeddings = response.embeddings as + | Array> + | undefined; + if (Array.isArray(embeddings) && embeddings.length > 0) { + for (let i = 0; i < embeddings.length; i++) { + const values = (embeddings[i]?.values ?? []) as number[]; + messages.push({ + role: "assistant", + content: safeStringify({ + index: i, + dimensions: values.length, + preview: values.slice(0, 5), + }), + }); + } + } + } + + return messages; } /** - * Extract and set completion content from candidates + * Accumulate a single streamed GenerateContentResponse chunk into a + * synthetic response dict. Safe against malformed chunks. + * + * @param accumulated - Mutable dict built up across chunks. + * @param chunk - A single GenerateContentResponse chunk from the stream. + * @param span - The active span (for time-to-first-token recording). + * @param startTime - Request start timestamp in ms. */ -function _setCompletionAttributes( +export function processStreamChunk( + accumulated: Record, + chunk: any, span: Span, - response: Record, + startTime: number, ): void { - const candidates = response.candidates as - | Array> - | undefined; - if (!Array.isArray(candidates)) return; - - for (let i = 0; i < candidates.length; i++) { - const candidate = candidates[i]; - const content = candidate.content as Record | undefined; - - if (!content) continue; - - const role = normalizeGenAIRole(String(content.role ?? "model")); - const parts = content.parts as Array> | undefined; - - if (!Array.isArray(parts)) continue; + try { + if (chunk.modelVersion) { + accumulated.modelVersion = chunk.modelVersion; + } + if (chunk.responseId) { + accumulated.responseId = chunk.responseId; + } - // Extract text from parts - const textContent = parts - .filter((p) => p.text !== undefined) - .map((p) => String(p.text)) - .join(""); + // Accumulate text + const chunkText = typeof chunk.text === "string" ? chunk.text : undefined; + if (chunkText && chunkText.length > 0) { + if (!accumulated._text) { + accumulated._text = chunkText; + span.setAttribute( + "gen_ai.performance.time_to_first_token", + (Date.now() - startTime) / 1000, + ); + } else { + accumulated._text += chunkText; + } + } - if (textContent) { - span.setAttribute(`${SpanAttributes.LLM_COMPLETIONS}.${i}.role`, role); - span.setAttribute( - `${SpanAttributes.LLM_COMPLETIONS}.${i}.content`, - textContent, - ); + // Accumulate function calls + const fcs = chunk.functionCalls; + if (Array.isArray(fcs) && fcs.length > 0) { + if (!accumulated._functionCalls) accumulated._functionCalls = []; + accumulated._functionCalls.push(...fcs); } - // Track function calls - const functionCalls = parts.filter((p) => p.functionCall !== undefined); - if (functionCalls.length > 0) { - span.setAttribute( - `gen_ai.completion.${i}.function_call_count`, - functionCalls.length, - ); + // Usage metadata -- later chunks overwrite; final chunk has full counts + if (chunk.usageMetadata) { + accumulated.usageMetadata = chunk.usageMetadata; + } - for (let j = 0; j < functionCalls.length; j++) { - const fc = functionCalls[j].functionCall as Record; - if (fc.name !== undefined) { - span.setAttribute( - `gen_ai.completion.${i}.function_call.${j}.name`, - String(fc.name), - ); - } + // Finish reason from candidates + if (Array.isArray(chunk.candidates) && chunk.candidates.length > 0) { + const reason = chunk.candidates[0]?.finishReason; + if (reason) { + if (!accumulated.candidates) accumulated.candidates = [{}]; + accumulated.candidates[0].finishReason = reason; } } + + if (Logger.isDebugMode()) { + span.addEvent("llm.content.completion.chunk"); + } + } catch (e) { + Logger.error(`${LOG_PREFIX}: processStreamChunk error`, e); } } /** - * Set attributes for embedding responses + * Convert accumulated stream data into the shape expected by + * setResponseAttributes. Called once when the stream completes. */ -function _setEmbeddingResponseAttributes( - span: Span, - response: Record, -): void { - // Single embedding response - const embedding = response.embedding as Record | undefined; - if (embedding?.values !== undefined) { - const values = embedding.values as number[]; - span.setAttribute("gen_ai.response.embedding_dimensions", values.length); - } +export function buildAccumulatedResponse( + accumulated: Record, +): Record { + const response: Record = { + responseId: accumulated.responseId, + modelVersion: accumulated.modelVersion, + usageMetadata: accumulated.usageMetadata, + candidates: accumulated.candidates, + }; - // Batch embedding response - const embeddings = response.embeddings as - | Array> - | undefined; - if (Array.isArray(embeddings)) { - span.setAttribute("gen_ai.response.embedding_count", embeddings.length); - if (embeddings.length > 0 && embeddings[0].values !== undefined) { - const values = embeddings[0].values as number[]; - span.setAttribute("gen_ai.response.embedding_dimensions", values.length); - } + if (accumulated._text) { + response.text = accumulated._text; + } + if (accumulated._functionCalls) { + response.functionCalls = accumulated._functionCalls; } + + return response; } diff --git a/src/instrumentation/google-genai/version.ts b/src/instrumentation/google-genai/version.ts index f04a821..5a10cbb 100644 --- a/src/instrumentation/google-genai/version.ts +++ b/src/instrumentation/google-genai/version.ts @@ -1,5 +1 @@ -/** - * Version information for Google GenAI instrumentation - */ - export const __version__ = "1.0.0"; diff --git a/src/instrumentation/google-genai/wrappers.ts b/src/instrumentation/google-genai/wrappers.ts index 45def30..724fc2e 100644 --- a/src/instrumentation/google-genai/wrappers.ts +++ b/src/instrumentation/google-genai/wrappers.ts @@ -1,108 +1,151 @@ +/** + * Shimmer wrapper factories for @google/genai instrumentation. + * + * Two wrapper types: + * genericWrapper — for generateContent, embedContent, sendMessage + * streamWrapper — for generateContentStream, sendMessageStream + * + * All wrappers use the shared wrapResponse() infrastructure to handle + * promises and async iterables uniformly. Netra errors are isolated + * from user code; user/API errors are always recorded on the span and + * re-thrown. + */ + import { Span, SpanKind, SpanStatusCode, Tracer, context, + trace, } from "@opentelemetry/api"; import { Logger } from "../../logger"; +import { wrapResponse } from "../../utils/response-handler"; import { - isPromise, + createSuppressedContext, modelAsDict, shouldSuppressInstrumentation, } from "../utils"; -import { extractModelName, setRequestAttributes, setResponseAttributes } from "./utils"; +import { GoogleGenAIRequestType, SPAN_NAMES } from "./types"; +import { + buildAccumulatedResponse, + processStreamChunk, + setRequestAttributes, + setResponseAttributes, +} from "./utils"; +import { SpanAttributes } from "../span-attributes"; -type GoogleGenAIRequestType = "chat" | "embedding"; +const LOG_PREFIX = "netra.instrumentation.google_genai"; -const CHAT_SPAN_NAME = "google_genai.chat"; -const EMBEDDING_SPAN_NAME = "google_genai.embedding"; +/** + * Build a params dict from the first argument and the `this` context + * (Models or Chat instance). Shared by both wrapper factories. + */ +function buildParams(args: any[], self: Record): Record { + const raw = args[0]; + const params: Record = + typeof raw === "object" && raw !== null ? { ...raw } : { message: raw }; + + if (!params.model && self.model) { + params.model = self.model; + } + if (!params.config && self.config) { + params.config = self.config; + } + + // Chat.getHistory(true) returns the internal history array including + // the pending user message. Wrapped in try/catch in case the SDK + // changes the method signature or it has unexpected side-effects. + try { + const history = + typeof (self as any).getHistory === "function" + ? (self as any).getHistory(true) + : self.history; + if (Array.isArray(history)) { + params._history = history; + } + } catch { + // Fall back silently — history is best-effort for tracing + } + + return params; +} -function googleGenAIWrapper( +/** + * Wrapper factory for non-streaming SDK methods: + * Models.generateContent, Models.embedContent, Chat.sendMessage + * + * Creates a CLIENT span, sets request/response attributes, and delegates + * return-type dispatch (sync / Promise / AsyncIterable) to wrapResponse(). + */ +function genericWrapperFactory( tracer: Tracer, spanName: string, requestType: GoogleGenAIRequestType, ) { return function wrapper any>(original: F): F { - return function (this: unknown, ...args: Parameters): any { + return function (this: unknown, ...args: any[]) { if (shouldSuppressInstrumentation()) { return original.apply(this, args); } - let kwargs: Record = {}; - const modelInstance = this as Record; - const modelName = modelInstance.model as string | undefined; - const systemInstruction = modelInstance.systemInstruction as - | unknown - | undefined; - const history = modelInstance.history as unknown | undefined; - - if(modelName) { - kwargs.model = extractModelName(modelName); - } - if (systemInstruction) { - kwargs.systemInstruction = systemInstruction; - } - if (history) { - kwargs.history = history; - } + const self = this as Record; + const params = buildParams(args, self); const currentContext = context.active(); + return tracer.startActiveSpan( spanName, - { - kind: SpanKind.CLIENT, - attributes: { "llm.request.type": requestType }, - }, - currentContext, + { kind: SpanKind.CLIENT }, (span: Span) => { try { - setRequestAttributes(span, kwargs, requestType, args[0]); - const startTime = Date.now(); - const response = original.apply(this, args); + setRequestAttributes(span, params, requestType); - if (isPromise(response)) { - return (async () => { - try { - const value = await response; + const startTime = Date.now(); + const spanContext = trace.setSpan(currentContext, span); + const suppressedCtx = createSuppressedContext(spanContext); + const response = context.with(suppressedCtx, () => + original.apply(this, args), + ); + + return wrapResponse( + response, + { + withContext: (fn) => context.with(spanContext, fn), + onSuccess: (value) => { const endTime = Date.now(); const responseDict = modelAsDict(value); + // Preserve getter-based properties that JSON serialization drops + if (typeof (value as any)?.text === "string") { + responseDict.text = (value as any).text; + } + if (Array.isArray((value as any)?.functionCalls)) { + responseDict.functionCalls = (value as any).functionCalls; + } setResponseAttributes(span, responseDict); - const duration = (endTime - startTime) / 1000; - span.setAttribute("llm.response.duration", duration); span.setAttribute( - "gen_ai.performance.time_to_first_token", - duration, + SpanAttributes.LLM_RESPONSE_DURATION, + (endTime - startTime) / 1000, ); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return value; - } catch (error) { - Logger.error("netra.instrumentation.google-genai:", error); + }, + onError: (error) => { span.setStatus({ code: SpanStatusCode.ERROR, message: error instanceof Error ? error.message : String(error), }); span.recordException(error as Error); + }, + finalize: (status) => { + if (status === "ok") { + span.setStatus({ code: SpanStatusCode.OK }); + } span.end(); - throw error; - } - })(); - } else { - const endTime = Date.now(); - const responseDict = modelAsDict(response); - setResponseAttributes(span, responseDict); - span.setAttribute( - "llm.response.duration", - (endTime - startTime) / 1000, - ); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return response; - } + }, + }, + { preserveOriginal: response }, + ); } catch (error) { - Logger.error("netra.instrumentation.google-genai:", error); span.setStatus({ code: SpanStatusCode.ERROR, message: error instanceof Error ? error.message : String(error), @@ -117,29 +160,28 @@ function googleGenAIWrapper( }; } -function googleGenAIStreamWrapper( +/** + * Wrapper factory for streaming SDK methods: + * Models.generateContentStream, Chat.sendMessageStream + * + * The SDK returns Promise>. + * wrapResponse handles the Promise -> AsyncIterable dispatch; onChunk + * accumulates each GenerateContentResponse chunk, and finalize writes + * the combined result to the span. + */ +function streamWrapperFactory( tracer: Tracer, spanName: string, requestType: GoogleGenAIRequestType, ) { return function wrapper any>(original: F): F { - return function (this: unknown, ...args: Parameters): any { + return function (this: unknown, ...args: any[]) { if (shouldSuppressInstrumentation()) { return original.apply(this, args); } - let kwargs: Record = {}; - - const modelInstance = this as Record; - const modelName = modelInstance.model as string | undefined; - const systemInstruction = modelInstance.systemInstruction as - | unknown - | undefined; - const history = modelInstance.history as unknown | undefined; - - if (modelName) kwargs.model = extractModelName(modelName); - if (systemInstruction) kwargs.systemInstruction = systemInstruction; - if (history) kwargs.history = history; + const self = this as Record; + const params = buildParams(args, self); const currentContext = context.active(); @@ -147,172 +189,58 @@ function googleGenAIStreamWrapper( spanName, { kind: SpanKind.CLIENT, - attributes: { "llm.request.type": requestType }, + attributes: { [SpanAttributes.LLM_IS_STREAMING]: true }, }, - currentContext, (span: Span) => { const startTime = Date.now(); + const accumulated: Record = {}; try { - setRequestAttributes(span, kwargs, requestType, args[0]); - - const response = original.apply(this, args); - - // generateContentStream() is async -> Promise - if (!isPromise(response)) { - // If SDK changes to sync stream, still handle it safely - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return response; - } - - return (async () => { - try { - const streamResult: any = await response; - - // Google GenAI stream result typically looks like: - // { stream: AsyncIterable, response?: Promise } - // We will wrap streamResult.stream so we can end span at completion. - const originalStream: AsyncIterable = streamResult.stream; - - if ( - !originalStream || - typeof originalStream[Symbol.asyncIterator] !== "function" - ) { - // Not a real stream, treat like non-stream - const endTime = Date.now(); - const responseDict = modelAsDict(streamResult); - setResponseAttributes(span, responseDict); - const duration = (endTime - startTime) / 1000; - span.setAttribute("llm.response.duration", duration); - span.setAttribute( - "gen_ai.performance.time_to_first_token", - duration, - ); - span.setStatus({ code: SpanStatusCode.OK }); + setRequestAttributes(span, params, requestType); + + const spanContext = trace.setSpan(currentContext, span); + const suppressedCtx = createSuppressedContext(spanContext); + const response = context.with(suppressedCtx, () => + original.apply(this, args), + ); + + return wrapResponse( + response, + { + withContext: (fn) => context.with(spanContext, fn), + onChunk: (chunk) => { + processStreamChunk(accumulated, chunk, span, startTime); + }, + onError: (error) => { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: + error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + }, + finalize: (status) => { + try { + const endTime = Date.now(); + const syntheticResponse = + buildAccumulatedResponse(accumulated); + setResponseAttributes(span, syntheticResponse); + span.setAttribute( + SpanAttributes.LLM_RESPONSE_DURATION, + (endTime - startTime) / 1000, + ); + } catch (e) { + Logger.error(`${LOG_PREFIX}: stream finalize error`, e); + } + if (status === "ok") { + span.setStatus({ code: SpanStatusCode.OK }); + } span.end(); - return streamResult; - } - - let chunkIndex = 0; - let finalText = ""; - let firstTokenRecorded = false; - - const wrappedStream: AsyncIterable = { - [Symbol.asyncIterator]() { - const iterator = originalStream[Symbol.asyncIterator](); - return { - async next() { - try { - const res = await iterator.next(); - - // res = { value, done } - if (res?.done) { - const endTime = Date.now(); - - // Await the response promise if available to get full metadata (token counts, etc.) - if ( - streamResult.response && - isPromise(streamResult.response) - ) { - try { - const finalResponse = - await streamResult.response; - const responseDict = modelAsDict(finalResponse); - setResponseAttributes(span, responseDict); - } catch { - // If response promise fails, still set what we have from stream - const responseDict = modelAsDict(streamResult); - setResponseAttributes(span, responseDict); - } - } else { - // Fallback: set attributes from streamResult - const responseDict = modelAsDict(streamResult); - setResponseAttributes(span, responseDict); - } - - const duration = (endTime - startTime) / 1000; - span.setAttribute( - "llm.response.duration", - duration, - ); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return res; - } - - const chunk = res.value; - - // Optional: store chunk-by-chunk attributes if you want - // span.setAttribute(`llm.stream.chunk.${chunkIndex}`, ...) - // Best-effort: accumulate chunk.text() if available - try { - const t = - typeof chunk?.text === "function" - ? chunk.text() - : chunk?.text; - if (typeof t === "string") { - if (t && !firstTokenRecorded) { - span.setAttribute( - "gen_ai.performance.time_to_first_token", - (Date.now() - startTime) / 1000, - ); - firstTokenRecorded = true; - } - finalText += t; - } - } catch { - // ignore chunk parsing issues - } - - chunkIndex += 1; - return res; - } catch (error) { - // End span on streaming error - span.setStatus({ - code: SpanStatusCode.ERROR, - message: - error instanceof Error - ? error.message - : String(error), - }); - span.recordException(error as Error); - span.end(); - throw error; - } - }, - async return() { - // Called if consumer stops early (break) - const endTime = Date.now(); - const duration = (endTime - startTime) / 1000; - span.setAttribute("llm.response.duration", duration); - span.setStatus({ code: SpanStatusCode.OK }); - span.end(); - return { value: undefined, done: true }; - }, - }; - }, - }; - - // Return same object but with wrapped stream - return { - ...streamResult, - stream: wrappedStream, - }; - } catch (error) { - Logger.error("netra.instrumentation.google-genai:", error); - span.setStatus({ - code: SpanStatusCode.ERROR, - message: - error instanceof Error ? error.message : String(error), - }); - span.recordException(error as Error); - span.end(); - throw error; - } - })(); + }, + }, + { preserveOriginal: response }, + ); } catch (error) { - Logger.error("netra.instrumentation.google-genai:", error); span.setStatus({ code: SpanStatusCode.ERROR, message: error instanceof Error ? error.message : String(error), @@ -327,66 +255,11 @@ function googleGenAIStreamWrapper( }; } -/** - * Wraps startChat to instrument the returned ChatSession's sendMessage - * and sendMessageStream methods with proper tracing. - */ -function googleGenAIStartChatWrapper(tracer: Tracer, spanName: string, requestType: GoogleGenAIRequestType) { - const sendMessageWrapperFn = googleGenAIWrapper(tracer, spanName, requestType); - const sendMessageStreamWrapperFn = googleGenAIStreamWrapper(tracer, spanName, requestType); - - return function wrapper any>(original: F): F { - return function (this: unknown, ...args: Parameters): any { - const chatSession = original.apply(this, args); - if (!chatSession) return chatSession; - - const modelInstance = this as Record; - const modelName = modelInstance.model as string | undefined; - const systemInstruction = modelInstance.systemInstruction as unknown | undefined; - const chatHistory = (args[0] as Record | undefined)?.history; - - if (typeof chatSession.sendMessage === "function" && !chatSession.__netra_patched) { - const originalSendMessage = chatSession.sendMessage.bind(chatSession); - const wrappedSendMessage = sendMessageWrapperFn(originalSendMessage); - - chatSession.sendMessage = function (this: unknown, ...sendArgs: any[]) { - const ctx = this as Record; - if (modelName) ctx.model = modelName; - if (systemInstruction) ctx.systemInstruction = systemInstruction; - if (chatHistory) ctx.history = chatHistory; - return wrappedSendMessage.apply(this, sendArgs); - }; - - if (typeof chatSession.sendMessageStream === "function") { - const originalSendStream = chatSession.sendMessageStream.bind(chatSession); - const wrappedSendStream = sendMessageStreamWrapperFn(originalSendStream); - - chatSession.sendMessageStream = function (this: unknown, ...sendArgs: any[]) { - const ctx = this as Record; - if (modelName) ctx.model = modelName; - if (systemInstruction) ctx.systemInstruction = systemInstruction; - if (chatHistory) ctx.history = chatHistory; - return wrappedSendStream.apply(this, sendArgs); - }; - } - - chatSession.__netra_patched = true; - } - - return chatSession; - } as unknown as F; - }; -} - -/* Specific wrappers for different requests */ export const chatWrapper = (tracer: Tracer) => - googleGenAIWrapper(tracer, CHAT_SPAN_NAME, "chat"); - -export const embeddingsWrapper = (tracer: Tracer) => - googleGenAIWrapper(tracer, EMBEDDING_SPAN_NAME, "embedding"); + genericWrapperFactory(tracer, SPAN_NAMES.CHAT, "chat"); export const chatStreamWrapper = (tracer: Tracer) => - googleGenAIStreamWrapper(tracer, CHAT_SPAN_NAME, "chat"); + streamWrapperFactory(tracer, SPAN_NAMES.CHAT, "chat"); -export const startChatWrapper = (tracer: Tracer) => - googleGenAIStartChatWrapper(tracer, CHAT_SPAN_NAME, "chat"); +export const embeddingsWrapper = (tracer: Tracer) => + genericWrapperFactory(tracer, SPAN_NAMES.EMBEDDING, "embedding"); diff --git a/src/instrumentation/google-generative-ai/index.ts b/src/instrumentation/google-generative-ai/index.ts new file mode 100644 index 0000000..a568236 --- /dev/null +++ b/src/instrumentation/google-generative-ai/index.ts @@ -0,0 +1,116 @@ +/** + * Google Generative AI (@google/generative-ai) instrumentor for Netra SDK. + * + * Patches GenerativeModel.prototype methods (generateContent, + * generateContentStream, embedContent) and ChatSession.prototype + * methods (sendMessage, sendMessageStream) to produce OTel spans. + */ + +import { Tracer } from "@opentelemetry/api"; +import shimmer from "shimmer"; +import { Logger } from "../../logger"; +import { BaseInstrumentor } from "../base-instrumentor"; +import { __version__ } from "./version"; +import { + chatStreamWrapper, + chatWrapper, + embeddingsWrapper, +} from "./wrappers"; + +interface GoogleGenerativeAIClasses { + GenerativeModel: any; + ChatSession?: any; +} + +export class NetraGoogleGenerativeAIInstrumentor extends BaseInstrumentor { + protected readonly instrumentationName = "netra.instrumentation.google_generative_ai"; + protected readonly instrumentationVersion = __version__; + protected readonly packageName = "@google/generative-ai"; + protected readonly displayName = "Google Generative AI"; + + protected extractClasses(mod: any): GoogleGenerativeAIClasses | null { + const root = mod.default ?? mod; + const GenerativeModel = + root.GenerativeModel ?? root; + if (!GenerativeModel?.prototype) return null; + return { GenerativeModel, ChatSession: root.ChatSession }; + } + + protected isSameClasses(a: GoogleGenerativeAIClasses, b: GoogleGenerativeAIClasses): boolean { + return a.GenerativeModel === b.GenerativeModel; + } + + protected applyPatches(classes: GoogleGenerativeAIClasses, tracer: Tracer): boolean { + const proto = classes.GenerativeModel?.prototype; + if (!proto) { + Logger.error("Google Generative AI: GenerativeModel.prototype not found"); + return false; + } + + let wrapped = false; + + if (typeof proto.generateContent === "function") { + shimmer.wrap(proto, "generateContent", chatWrapper(tracer)); + wrapped = true; + } + if (typeof proto.generateContentStream === "function") { + shimmer.wrap(proto, "generateContentStream", chatStreamWrapper(tracer)); + wrapped = true; + } + if (typeof proto.embedContent === "function") { + shimmer.wrap(proto, "embedContent", embeddingsWrapper(tracer)); + wrapped = true; + } + + const chatProto = classes.ChatSession?.prototype; + if (chatProto) { + if (typeof chatProto.sendMessage === "function") { + shimmer.wrap(chatProto, "sendMessage", chatWrapper(tracer)); + wrapped = true; + } + if (typeof chatProto.sendMessageStream === "function") { + shimmer.wrap(chatProto, "sendMessageStream", chatStreamWrapper(tracer)); + wrapped = true; + } + } + + return wrapped; + } + + protected removePatches(classes: GoogleGenerativeAIClasses): void { + const proto = classes.GenerativeModel?.prototype; + if (proto) { + if (typeof proto.generateContent === "function") + shimmer.unwrap(proto, "generateContent"); + if (typeof proto.generateContentStream === "function") + shimmer.unwrap(proto, "generateContentStream"); + if (typeof proto.embedContent === "function") + shimmer.unwrap(proto, "embedContent"); + } + + const chatProto = classes.ChatSession?.prototype; + if (chatProto) { + if (typeof chatProto.sendMessage === "function") + shimmer.unwrap(chatProto, "sendMessage"); + if (typeof chatProto.sendMessageStream === "function") + shimmer.unwrap(chatProto, "sendMessageStream"); + } + } + + /** + * @deprecated Use instrument() instead. Kept for backward compatibility + * with orchestrator call sites that haven't been updated yet. + */ + async instrumentAsync( + options: { tracerProvider?: any } = {}, + ): Promise { + return this.instrument(options); + } +} + +export const googleGenerativeAIInstrumentor = + new NetraGoogleGenerativeAIInstrumentor(); + +export { chatWrapper, chatStreamWrapper, embeddingsWrapper } from "./wrappers"; +export { setRequestAttributes, setResponseAttributes } from "./utils"; +export { __version__ } from "./version"; diff --git a/src/instrumentation/google-generative-ai/utils.ts b/src/instrumentation/google-generative-ai/utils.ts new file mode 100644 index 0000000..c17a291 --- /dev/null +++ b/src/instrumentation/google-generative-ai/utils.ts @@ -0,0 +1,633 @@ +/** + * Utility functions for Google Generative AI instrumentation + * + * Google Generative AI has a different response format than OpenAI: + * - Response: { response: EnhancedGenerateContentResponse } + * - EnhancedGenerateContentResponse: { candidates, usageMetadata, promptFeedback } + * - UsageMetadata: { promptTokenCount, candidatesTokenCount, totalTokenCount, cachedContentTokenCount } + */ + +import { Span } from "@opentelemetry/api"; +import { safeStringify } from "../../utils/serialization"; +import { SpanAttributes } from "../span-attributes"; +import { isTraceContentEnabled } from "../utils"; + +/** + * Extract the model name from the model string. + * @param model - The model string. + * @returns The model name without the "models/" prefix if it exists. + */ +export function extractModelName(model: string): string { + if (model && model.startsWith("models/")) { + return model.replace(/^models\//, ""); + } + return model; +} + +/** + * Normalize role values from Google Generative AI. + * + * Google Generative AI uses "model" to indicate the assistant role. + * This function maps "model" → "assistant" and returns any other role unchanged in lowercase. + */ +function normalizeGenerativeAIRole(raw: string): string { + const rawLower = raw.toLowerCase(); + return rawLower === "model" ? "assistant" : rawLower; +} + +export function setRequestAttributes( + span: Span, + kwargs: Record, + requestType: string, + args: Record, +): void { + // Use a private property on the span to store kwargs temporarily for setResponseAttributes + (span as any)._netra_kwargs = kwargs; + if (!span.isRecording()) { + return; + } + + span.setAttribute(SpanAttributes.LLM_REQUEST_TYPE, requestType); + span.setAttribute(SpanAttributes.LLM_SYSTEM, "google_generative_ai"); + + // Model is set on the GenerativeModel instance, not in the request kwargs + // We need to access it from `this.model` in the wrapper if available + // For now, set from kwargs if provided + if (kwargs.model !== undefined) { + span.setAttribute(SpanAttributes.LLM_REQUEST_MODEL, String(kwargs.model)); + } + + // Generation config parameters (from generationConfig object or direct kwargs) + const generationConfig = + (kwargs.generationConfig as Record) ?? kwargs; + + if (generationConfig.temperature !== undefined) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_TEMPERATURE, + Number(generationConfig.temperature), + ); + } + + if (generationConfig.topP !== undefined) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_TOP_P, + Number(generationConfig.topP), + ); + } + + if (generationConfig.topK !== undefined) { + span.setAttribute("gen_ai.request.top_k", Number(generationConfig.topK)); + } + + if (generationConfig.maxOutputTokens !== undefined) { + span.setAttribute( + SpanAttributes.LLM_REQUEST_MAX_TOKENS, + Number(generationConfig.maxOutputTokens), + ); + } + + if (generationConfig.stopSequences !== undefined) { + span.setAttribute( + SpanAttributes.LLM_CHAT_STOP_SEQUENCES, + safeStringify(generationConfig.stopSequences), + ); + } + + // Candidate count + if (generationConfig.candidateCount !== undefined) { + span.setAttribute( + "gen_ai.request.candidate_count", + Number(generationConfig.candidateCount), + ); + } + + // Presence/frequency penalty + if (generationConfig.presencePenalty !== undefined) { + span.setAttribute( + SpanAttributes.LLM_PRESENCE_PENALTY, + Number(generationConfig.presencePenalty), + ); + } + if (generationConfig.frequencyPenalty !== undefined) { + span.setAttribute( + SpanAttributes.LLM_FREQUENCY_PENALTY, + Number(generationConfig.frequencyPenalty), + ); + } + + // Embedding dimensions + if (kwargs.dimensions !== undefined) { + span.setAttribute("gen_ai.request.dimensions", Number(kwargs.dimensions)); + } + + // Tools + if (Array.isArray(kwargs.tools) && kwargs.tools.length > 0) { + span.setAttribute("gen_ai.request.tools_count", kwargs.tools.length); + } + + // Tool config + if (kwargs.toolConfig !== undefined) { + span.setAttribute( + "gen_ai.request.tool_config", + safeStringify(kwargs.toolConfig), + ); + } + + // Safety settings + if ( + Array.isArray(kwargs.safetySettings) && + kwargs.safetySettings.length > 0 + ) { + span.setAttribute( + "gen_ai.request.safety_settings_count", + kwargs.safetySettings.length, + ); + } + + // System instruction + if (kwargs.systemInstruction !== undefined) { + if (isTraceContentEnabled()) { + span.setAttribute( + "gen_ai.request.system_instruction", + safeStringify(kwargs.systemInstruction), + ); + } + span.setAttribute("gen_ai.request.has_system_instruction", true); + } + + // Content tracing - prompts + if (isTraceContentEnabled()) { + _setPromptAttributes(span, kwargs, args); + } +} + +/** + * Extract and set prompt content from Google Generative AI request + */ +function _setPromptAttributes( + span: Span, + kwargs: Record, + args: any, +): void { + // For generateContent, the prompt can be: + // 1. A string (simple prompt) + // 2. An array of Parts (Array) + // 3. A GenerateContentRequest object with contents array + + let promptIndex = 0; + + // 1. Add system instruction if present (from getGenerativeModel) + if (kwargs.systemInstruction !== undefined) { + const systemInstruction = kwargs.systemInstruction as any; + let systemContent = ""; + + if (typeof systemInstruction === "string") { + systemContent = systemInstruction; + } else if ( + systemInstruction.parts && + Array.isArray(systemInstruction.parts) + ) { + systemContent = systemInstruction.parts + .filter((p: any) => p.text !== undefined) + .map((p: any) => String(p.text)) + .join(""); + } else if (systemInstruction.text) { + systemContent = String(systemInstruction.text); + } else { + systemContent = safeStringify(systemInstruction); + } + + if (systemContent) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, + "system", + ); + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + systemContent, + ); + promptIndex++; + } + } + + // 2. Chat history from startChat (multiturn context) + if (kwargs.history && Array.isArray(kwargs.history)) { + for (const turn of kwargs.history as Array>) { + const role = normalizeGenerativeAIRole(String(turn.role ?? "user")); + const parts = turn.parts as Array> | undefined; + if (Array.isArray(parts)) { + const textContent = parts + .filter((p) => p.text !== undefined) + .map((p) => String(p.text)) + .join(""); + if (textContent) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, + role, + ); + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + textContent, + ); + promptIndex++; + } + } + } + } + + // 3. Add prompts from args (generateContent/embedContent call) + if (!args) return; + + // Handle string prompt + if (typeof args === "string") { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, + "user", + ); + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + args, + ); + promptIndex++; + return; + } + + // Handle Array + if (Array.isArray(args)) { + const textParts = args + .map((p: any) => { + if (typeof p === "string") return p; + if (p && typeof p.text === "string") return p.text; + return ""; + }) + .filter(Boolean) + .join(" "); + + if (textParts) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.role`, + "user", + ); + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + textParts, + ); + promptIndex++; + } + return; + } + + // Handle GenerateContentRequest object { contents: [...] } + const contents = args.contents as Array> | undefined; + if (Array.isArray(contents)) { + for (const content of contents) { + const role = normalizeGenerativeAIRole(String(content.role ?? "user")); + const parts = content.parts as Array> | undefined; + + if (Array.isArray(parts)) { + const textParts = parts + .filter((p) => p.text !== undefined) + .map((p) => String(p.text)) + .join(""); + + const inlineDataParts = parts.filter((p) => p.inlineData !== undefined); + + // Reserve a prompt slot for this content block regardless of whether + // it has text, so inline-data metadata always references a valid index. + const slotIndex = promptIndex; + + if (textParts || inlineDataParts.length > 0) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${slotIndex}.role`, + role, + ); + if (textParts) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${slotIndex}.content`, + textParts, + ); + } + promptIndex++; + } + + if (inlineDataParts.length > 0) { + span.setAttribute( + `gen_ai.prompt.${slotIndex}.has_inline_data`, + true, + ); + span.setAttribute( + `gen_ai.prompt.${slotIndex}.inline_data_count`, + inlineDataParts.length, + ); + } + } + } + } + + // For embedContent, handle content object { parts: [...] } or string + if (args.content !== undefined) { + const content = args.content as Record | string; + if (typeof content === "string") { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + content, + ); + promptIndex++; + } else if (content.parts !== undefined) { + const parts = content.parts as Array>; + const textContent = parts + .filter((p) => p.text !== undefined) + .map((p) => String(p.text)) + .join(""); + if (textContent) { + span.setAttribute( + `${SpanAttributes.LLM_PROMPTS}.${promptIndex}.content`, + textContent, + ); + promptIndex++; + } + } + } +} + +/** + * Set response attributes for Google Generative AI responses + * Handles the specific structure of GenerateContentResult + */ +export function setResponseAttributes( + span: Span, + response: Record, +): void { + if (!span.isRecording()) { + return; + } + + // Google Generative AI returns { response: EnhancedGenerateContentResponse } + // The response object itself is what we need to parse + const actualResponse = + (response.response as Record) ?? response; + + // Set usage metadata -- try actualResponse first, fall back to top-level + // response for embedding responses where usageMetadata may not survive + // the response.response unwrap or modelAsDict serialization + _setUsageAttributes(span, actualResponse); + if (!actualResponse.usageMetadata && response.usageMetadata) { + _setUsageAttributes(span, response); + } + + // Set candidate attributes + _setCandidateAttributes(span, actualResponse); + + // Set prompt feedback if present (content filtering) + _setPromptFeedbackAttributes(span, actualResponse); + + // Set completion content if tracing is enabled + if (isTraceContentEnabled()) { + _setCompletionAttributes(span, actualResponse); + } + + // Handle embedding response + _setEmbeddingResponseAttributes(span, actualResponse); +} + +/** + * Extract and set token usage from usageMetadata + */ +function _setUsageAttributes( + span: Span, + response: Record, +): void { + const usageMetadata = response.usageMetadata as + | Record + | undefined; + if (!usageMetadata) return; + + // Prompt tokens + if (usageMetadata.promptTokenCount !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_PROMPT_TOKENS, + Number(usageMetadata.promptTokenCount), + ); + } + + // Completion/candidates tokens + if (usageMetadata.candidatesTokenCount !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_COMPLETION_TOKENS, + Number(usageMetadata.candidatesTokenCount), + ); + } + + // Total tokens + if (usageMetadata.totalTokenCount !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_TOTAL_TOKENS, + Number(usageMetadata.totalTokenCount), + ); + } + + // Cached content tokens + if (usageMetadata.cachedContentTokenCount !== undefined) { + span.setAttribute( + SpanAttributes.LLM_USAGE_CACHE_READ_INPUT_TOKENS, + Number(usageMetadata.cachedContentTokenCount), + ); + } +} + +/** + * Extract and set attributes from candidates + */ +function _setCandidateAttributes( + span: Span, + response: Record, +): void { + const candidates = response.candidates as + | Array> + | undefined; + if (!Array.isArray(candidates) || candidates.length === 0) return; + + span.setAttribute("gen_ai.response.candidate_count", candidates.length); + + const firstCandidate = candidates[0]; + + // Finish reason + if (firstCandidate.finishReason !== undefined) { + span.setAttribute( + "gen_ai.response.finish_reason", + String(firstCandidate.finishReason), + ); + } + + // Average log probs (if present) + if (firstCandidate.avgLogprobs !== undefined) { + span.setAttribute( + "gen_ai.response.avg_logprobs", + Number(firstCandidate.avgLogprobs), + ); + } + + // Safety ratings + const safetyRatings = firstCandidate.safetyRatings as + | Array> + | undefined; + if (Array.isArray(safetyRatings) && safetyRatings.length > 0) { + span.setAttribute( + "gen_ai.response.safety_ratings_count", + safetyRatings.length, + ); + + // Set individual safety ratings + for (let i = 0; i < safetyRatings.length; i++) { + const rating = safetyRatings[i]; + if (rating.category !== undefined) { + span.setAttribute( + `gen_ai.response.safety_rating.${i}.category`, + String(rating.category), + ); + } + if (rating.probability !== undefined) { + span.setAttribute( + `gen_ai.response.safety_rating.${i}.probability`, + String(rating.probability), + ); + } + } + } + + // Citation metadata + const citationMetadata = firstCandidate.citationMetadata as + | Record + | undefined; + if (citationMetadata?.citationSources !== undefined) { + const sources = citationMetadata.citationSources as Array; + span.setAttribute("gen_ai.response.citation_count", sources.length); + } + + // Grounding metadata + if (firstCandidate.groundingMetadata !== undefined) { + span.setAttribute("gen_ai.response.has_grounding", true); + } +} + +/** + * Set prompt feedback attributes (content filtering info) + */ +function _setPromptFeedbackAttributes( + span: Span, + response: Record, +): void { + const promptFeedback = response.promptFeedback as + | Record + | undefined; + if (!promptFeedback) return; + + if (promptFeedback.blockReason !== undefined) { + span.setAttribute( + "gen_ai.response.prompt_block_reason", + String(promptFeedback.blockReason), + ); + } + + if (promptFeedback.blockReasonMessage !== undefined) { + span.setAttribute( + "gen_ai.response.prompt_block_message", + String(promptFeedback.blockReasonMessage), + ); + } + + const safetyRatings = promptFeedback.safetyRatings as + | Array> + | undefined; + if (Array.isArray(safetyRatings)) { + span.setAttribute( + "gen_ai.response.prompt_safety_ratings_count", + safetyRatings.length, + ); + } +} + +/** + * Extract and set completion content from candidates + */ +function _setCompletionAttributes( + span: Span, + response: Record, +): void { + const candidates = response.candidates as + | Array> + | undefined; + if (!Array.isArray(candidates)) return; + + for (let i = 0; i < candidates.length; i++) { + const candidate = candidates[i]; + const content = candidate.content as Record | undefined; + + if (!content) continue; + + const role = normalizeGenerativeAIRole(String(content.role ?? "model")); + const parts = content.parts as Array> | undefined; + + if (!Array.isArray(parts)) continue; + + // Extract text from parts + const textContent = parts + .filter((p) => p.text !== undefined) + .map((p) => String(p.text)) + .join(""); + + if (textContent) { + span.setAttribute(`${SpanAttributes.LLM_COMPLETIONS}.${i}.role`, role); + span.setAttribute( + `${SpanAttributes.LLM_COMPLETIONS}.${i}.content`, + textContent, + ); + } + + // Track function calls + const functionCalls = parts.filter((p) => p.functionCall !== undefined); + if (functionCalls.length > 0) { + span.setAttribute( + `gen_ai.completion.${i}.function_call_count`, + functionCalls.length, + ); + + for (let j = 0; j < functionCalls.length; j++) { + const fc = functionCalls[j].functionCall as Record; + if (fc.name !== undefined) { + span.setAttribute( + `gen_ai.completion.${i}.function_call.${j}.name`, + String(fc.name), + ); + } + } + } + } +} + +/** + * Set attributes for embedding responses + */ +function _setEmbeddingResponseAttributes( + span: Span, + response: Record, +): void { + // Single embedding response + const embedding = response.embedding as Record | undefined; + if (embedding?.values !== undefined) { + const values = embedding.values as number[]; + span.setAttribute("gen_ai.response.embedding_dimensions", values.length); + } + + // Batch embedding response + const embeddings = response.embeddings as + | Array> + | undefined; + if (Array.isArray(embeddings)) { + span.setAttribute("gen_ai.response.embedding_count", embeddings.length); + if (embeddings.length > 0 && embeddings[0].values !== undefined) { + const values = embeddings[0].values as number[]; + span.setAttribute("gen_ai.response.embedding_dimensions", values.length); + } + } +} diff --git a/src/instrumentation/google-generative-ai/version.ts b/src/instrumentation/google-generative-ai/version.ts new file mode 100644 index 0000000..efea73e --- /dev/null +++ b/src/instrumentation/google-generative-ai/version.ts @@ -0,0 +1,5 @@ +/** + * Version information for Google Generative AI instrumentation + */ + +export const __version__ = "1.0.0"; diff --git a/src/instrumentation/google-generative-ai/wrappers.ts b/src/instrumentation/google-generative-ai/wrappers.ts new file mode 100644 index 0000000..e60a8a3 --- /dev/null +++ b/src/instrumentation/google-generative-ai/wrappers.ts @@ -0,0 +1,365 @@ +import { + Span, + SpanKind, + SpanStatusCode, + Tracer, + context, +} from "@opentelemetry/api"; +import { Logger } from "../../logger"; +import { + isPromise, + modelAsDict, + shouldSuppressInstrumentation, +} from "../utils"; +import { extractModelName, setRequestAttributes, setResponseAttributes } from "./utils"; + +type GoogleGenerativeAIRequestType = "chat" | "embedding"; + +const LOG_PREFIX = "netra.instrumentation.google_generative_ai"; +const CHAT_SPAN_NAME = "google_generative_ai.chat"; +const EMBEDDING_SPAN_NAME = "google_generative_ai.embedding"; + +/** + * Build kwargs from the calling context (`this`). + * + * `this` is either a GenerativeModel (for generateContent/embedContent) + * or a ChatSession (for sendMessage/sendMessageStream). + * + * GenerativeModel stores config directly: this.generationConfig, this.tools, ... + * ChatSession stores config inside this.params: this.params.generationConfig, ... + * Both have this.model. + */ +function buildKwargs(instance: Record): Record { + const kwargs: Record = {}; + const params = instance.params as Record | undefined; + + const modelName = instance.model as string | undefined; + if (modelName) { + kwargs.model = extractModelName(modelName); + } + + const systemInstruction = instance.systemInstruction ?? params?.systemInstruction; + if (systemInstruction) kwargs.systemInstruction = systemInstruction; + + const history = (instance as any)._history ?? instance.history; + if (history) kwargs.history = history; + + const generationConfig = instance.generationConfig ?? params?.generationConfig; + if (generationConfig) kwargs.generationConfig = generationConfig; + + const safetySettings = instance.safetySettings ?? params?.safetySettings; + if (safetySettings) kwargs.safetySettings = safetySettings; + + const tools = instance.tools ?? params?.tools; + if (tools) kwargs.tools = tools; + + const toolConfig = instance.toolConfig ?? params?.toolConfig; + if (toolConfig) kwargs.toolConfig = toolConfig; + + return kwargs; +} + +function googleGenerativeAIWrapper( + tracer: Tracer, + spanName: string, + requestType: GoogleGenerativeAIRequestType, +) { + return function wrapper any>(original: F): F { + return function (this: unknown, ...args: Parameters): any { + if (shouldSuppressInstrumentation()) { + return original.apply(this, args); + } + + const modelInstance = this as Record; + const kwargs = buildKwargs(modelInstance); + + const currentContext = context.active(); + return tracer.startActiveSpan( + spanName, + { + kind: SpanKind.CLIENT, + attributes: { "llm.request.type": requestType }, + }, + currentContext, + (span: Span) => { + try { + try { + setRequestAttributes(span, kwargs, requestType, args[0]); + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + const startTime = Date.now(); + const response = original.apply(this, args); + + if (isPromise(response)) { + return (async () => { + try { + const value = await response; + try { + const endTime = Date.now(); + const responseDict = modelAsDict(value); + setResponseAttributes(span, responseDict); + const duration = (endTime - startTime) / 1000; + span.setAttribute("llm.response.duration", duration); + if (requestType !== "embedding") { + span.setAttribute( + "gen_ai.performance.time_to_first_token", + duration, + ); + } + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return value; + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: + error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + })(); + } else { + try { + const endTime = Date.now(); + const responseDict = modelAsDict(response); + setResponseAttributes(span, responseDict); + span.setAttribute( + "llm.response.duration", + (endTime - startTime) / 1000, + ); + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return response; + } + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + }, + ); + } as unknown as F; + }; +} + +function googleGenerativeAIStreamWrapper( + tracer: Tracer, + spanName: string, + requestType: GoogleGenerativeAIRequestType, +) { + return function wrapper any>(original: F): F { + return function (this: unknown, ...args: Parameters): any { + if (shouldSuppressInstrumentation()) { + return original.apply(this, args); + } + + const modelInstance = this as Record; + const kwargs = buildKwargs(modelInstance); + + const currentContext = context.active(); + + return tracer.startActiveSpan( + spanName, + { + kind: SpanKind.CLIENT, + attributes: { "llm.request.type": requestType }, + }, + currentContext, + (span: Span) => { + const startTime = Date.now(); + + try { + try { + setRequestAttributes(span, kwargs, requestType, args[0]); + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + + const response = original.apply(this, args); + + if (!isPromise(response)) { + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return response; + } + + return (async () => { + try { + const streamResult: any = await response; + + const originalStream: AsyncIterable = streamResult.stream; + + if ( + !originalStream || + typeof originalStream[Symbol.asyncIterator] !== "function" + ) { + try { + const endTime = Date.now(); + const responseDict = modelAsDict(streamResult); + setResponseAttributes(span, responseDict); + const duration = (endTime - startTime) / 1000; + span.setAttribute("llm.response.duration", duration); + span.setAttribute( + "gen_ai.performance.time_to_first_token", + duration, + ); + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return streamResult; + } + + let firstTokenRecorded = false; + + const wrappedStream: AsyncIterable = { + [Symbol.asyncIterator]() { + const iterator = originalStream[Symbol.asyncIterator](); + return { + async next() { + try { + const res = await iterator.next(); + + if (res?.done) { + try { + const endTime = Date.now(); + + if ( + streamResult.response && + isPromise(streamResult.response) + ) { + try { + const finalResponse = + await streamResult.response; + const responseDict = modelAsDict(finalResponse); + setResponseAttributes(span, responseDict); + } catch { + const responseDict = modelAsDict(streamResult); + setResponseAttributes(span, responseDict); + } + } else { + const responseDict = modelAsDict(streamResult); + setResponseAttributes(span, responseDict); + } + + const duration = (endTime - startTime) / 1000; + span.setAttribute( + "llm.response.duration", + duration, + ); + } catch (e) { + Logger.error(`${LOG_PREFIX}:`, e); + } + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return res; + } + + const chunk = res.value; + + try { + const t = + typeof chunk?.text === "function" + ? chunk.text() + : chunk?.text; + if (typeof t === "string") { + if (t && !firstTokenRecorded) { + span.setAttribute( + "gen_ai.performance.time_to_first_token", + (Date.now() - startTime) / 1000, + ); + firstTokenRecorded = true; + } + } + } catch { + // ignore chunk parsing issues + } + + return res; + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: + error instanceof Error + ? error.message + : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + }, + async return(value?: any) { + const endTime = Date.now(); + const duration = (endTime - startTime) / 1000; + span.setAttribute("llm.response.duration", duration); + span.setStatus({ code: SpanStatusCode.OK }); + span.end(); + return iterator.return?.(value) ?? { value: undefined, done: true as const }; + }, + async throw(e?: any) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: e instanceof Error ? e.message : String(e), + }); + span.recordException(e instanceof Error ? e : new Error(String(e))); + span.end(); + if (iterator.throw) return iterator.throw(e); + throw e; + }, + }; + }, + }; + + return { + ...streamResult, + stream: wrappedStream, + }; + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: + error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + })(); + } catch (error) { + span.setStatus({ + code: SpanStatusCode.ERROR, + message: error instanceof Error ? error.message : String(error), + }); + span.recordException(error as Error); + span.end(); + throw error; + } + }, + ); + } as unknown as F; + }; +} + +export const chatWrapper = (tracer: Tracer) => + googleGenerativeAIWrapper(tracer, CHAT_SPAN_NAME, "chat"); + +export const embeddingsWrapper = (tracer: Tracer) => + googleGenerativeAIWrapper(tracer, EMBEDDING_SPAN_NAME, "embedding"); + +export const chatStreamWrapper = (tracer: Tracer) => + googleGenerativeAIStreamWrapper(tracer, CHAT_SPAN_NAME, "chat"); diff --git a/src/instrumentation/index.ts b/src/instrumentation/index.ts index 7c58268..c2d0089 100644 --- a/src/instrumentation/index.ts +++ b/src/instrumentation/index.ts @@ -28,7 +28,8 @@ import { SpanIOProcessor, } from "../processors"; import { anthropicInstrumentor } from "./anthropic"; -import { googleGenerativeAIInstrumentor } from "./google-genai"; +import { googleGenAIInstrumentor } from "./google-genai"; +import { googleGenerativeAIInstrumentor } from "./google-generative-ai"; import { groqInstrumentor } from "./groq"; import { langgraphInstrumentor } from "./langgraph"; import { mistralAIInstrumentor } from "./mistralai"; @@ -36,7 +37,6 @@ import { openAIInstrumentor } from "./openai"; import { openaiAgentsInstrumentor } from "./openai-agents"; import { typeORMInstrumentor } from "./typeorm"; import { FilteringSpanExporter, TrialAwareOTLPExporter } from "../exporters"; -import { OTLPTraceExporter } from "@opentelemetry/exporter-trace-otlp-http"; import { LocalFilteringSpanProcessor } from "../processors/localfiltering-span-processor"; import { propagation } from "@opentelemetry/api"; import { @@ -300,6 +300,7 @@ export function initInstrumentations( mistral: false, langgraph: false, googleGenAI: false, + googleGenerativeAI: false, anthropic: false, openAiAgents: false, }; @@ -328,9 +329,12 @@ export function initInstrumentations( if (resolved.has(NetraInstruments.GROQ)) { customInstrumentModules.groq = true; } - if (resolved.has(NetraInstruments.GOOGLE_GENERATIVE_AI)) { + if (resolved.has(NetraInstruments.GOOGLE_GENAI)) { customInstrumentModules.googleGenAI = true; } + if (resolved.has(NetraInstruments.GOOGLE_GENERATIVE_AI)) { + customInstrumentModules.googleGenerativeAI = true; + } if (resolved.has(NetraInstruments.VERTEX_AI) && isPackageInstalled("@google-cloud/vertexai")) { instrumentModules.google_vertexai = require("@google-cloud/vertexai"); } @@ -369,7 +373,8 @@ export function initInstrumentations( if (blockAll || blockInstruments.has(NetraInstruments.GROQ)) customInstrumentModules.groq = false; if (blockAll || blockInstruments.has(NetraInstruments.MISTRAL)) customInstrumentModules.mistral = false; if (blockAll || blockInstruments.has(NetraInstruments.LANGGRAPH)) customInstrumentModules.langgraph = false; - if (blockAll || blockInstruments.has(NetraInstruments.GOOGLE_GENERATIVE_AI)) customInstrumentModules.googleGenAI = false; + if (blockAll || blockInstruments.has(NetraInstruments.GOOGLE_GENAI)) customInstrumentModules.googleGenAI = false; + if (blockAll || blockInstruments.has(NetraInstruments.GOOGLE_GENERATIVE_AI)) customInstrumentModules.googleGenerativeAI = false; if (blockAll || blockInstruments.has(NetraInstruments.ANTHROPIC)) customInstrumentModules.anthropic = false; if (blockAll || blockInstruments.has(NetraInstruments.OPENAI_AGENTS)) customInstrumentModules.openAiAgents = false; if (blockAll || blockInstruments.has(NetraInstruments.VERTEX_AI)) instrumentModules.google_vertexai = false; @@ -532,10 +537,22 @@ async function initCustomInstrumentationsAsync( if (customInstrumentModules.googleGenAI) { try { - await googleGenerativeAIInstrumentor.instrumentAsync({ tracerProvider }); + await googleGenAIInstrumentor.instrument({ tracerProvider }); Logger.debug("Custom Google GenAI instrumentation enabled"); } catch (e) { - Logger.debug("Failed to initialize custom Google GenAI instrumentation:", e); + Logger.debug( + "Failed to initialize custom Google GenAI instrumentation:", + e, + ); + } + } + + if (customInstrumentModules.googleGenerativeAI) { + try { + await googleGenerativeAIInstrumentor.instrument({ tracerProvider }); + Logger.debug("Custom Google Generative AI instrumentation enabled"); + } catch (e) { + Logger.debug("Failed to initialize custom Google Generative AI instrumentation:", e); } } @@ -908,14 +925,24 @@ export async function uninstrumentAll(): Promise { // Uninstrument custom Google GenAI instrumentation try { - if (googleGenerativeAIInstrumentor.isInstrumented()) { - googleGenerativeAIInstrumentor.uninstrument(); + if (googleGenAIInstrumentor.isInstrumented()) { + googleGenAIInstrumentor.uninstrument(); Logger.debug("Custom Google GenAI instrumentation disabled"); } } catch (e) { Logger.debug("Failed to uninstrument Google GenAI:", e); } + // Uninstrument custom Google Generative AI instrumentation + try { + if (googleGenerativeAIInstrumentor.isInstrumented()) { + googleGenerativeAIInstrumentor.uninstrument(); + Logger.debug("Custom Google Generative AI instrumentation disabled"); + } + } catch (e) { + Logger.debug("Failed to uninstrument Google Generative AI:", e); + } + // Uninstrument custom Langgraph instrumentation try { if (langgraphInstrumentor.isInstrumented()) { diff --git a/src/instrumentation/span-attributes.ts b/src/instrumentation/span-attributes.ts index 5b63bda..578810d 100644 --- a/src/instrumentation/span-attributes.ts +++ b/src/instrumentation/span-attributes.ts @@ -9,6 +9,7 @@ export const SpanAttributes = { LLM_REQUEST_MAX_TOKENS: "gen_ai.request.max_tokens", LLM_REQUEST_TEMPERATURE: "gen_ai.request.temperature", LLM_REQUEST_TOP_P: "gen_ai.request.top_p", + LLM_REQUEST_TOP_K: "gen_ai.request.top_k", LLM_REQUEST_REASONING: "gen_ai.request.reasoning", LLM_REQUEST_REASONING_EFFORT: "gen_ai.request.reasoning_effort", LLM_REQUEST_TOOL_NAME: "gen_ai.request.tool.name", @@ -16,6 +17,7 @@ export const SpanAttributes = { LLM_RESPONSE_MODEL: "gen_ai.response.model", LLM_RESPONSE_FINISH_REASON: "llm.response.finish_reason", + LLM_RESPONSE_DURATION: "llm.response.duration", LLM_USAGE_PROMPT_TOKENS: "gen_ai.usage.prompt_tokens", LLM_USAGE_COMPLETION_TOKENS: "gen_ai.usage.completion_tokens", diff --git a/src/instrumentation/utils.ts b/src/instrumentation/utils.ts index 18cdc80..ba5d43b 100644 --- a/src/instrumentation/utils.ts +++ b/src/instrumentation/utils.ts @@ -3,7 +3,7 @@ * Handles setting OTel span attributes for LLM request/response tracing. */ -import { Span, context } from "@opentelemetry/api"; +import { Span, context, type Context as OTelContext } from "@opentelemetry/api"; import { Config } from "../config"; import { Logger } from "../logger"; import { safeStringify } from "../utils/serialization"; @@ -43,6 +43,16 @@ export function shouldSuppressInstrumentation(): boolean { return ctx.getValue(SUPPRESS_INSTRUMENTATION_KEY) === true; } +/** + * Return a new context derived from `ctx` (default: active) with + * Netra instrumentation suppressed. Wrappers that call the original + * method within this context prevent nested google_genai spans (e.g. + * Chat.sendMessage → generateContentInternal). + */ +export function createSuppressedContext(ctx?: OTelContext): OTelContext { + return (ctx ?? context.active()).setValue(SUPPRESS_INSTRUMENTATION_KEY, true); +} + // Type Utilities — re-export from canonical location to avoid duplication export { isPromise } from "../utils/response-handler"; diff --git a/src/processors/instrumentation-span-processor.ts b/src/processors/instrumentation-span-processor.ts index a1b14be..1fc6e24 100644 --- a/src/processors/instrumentation-span-processor.ts +++ b/src/processors/instrumentation-span-processor.ts @@ -19,6 +19,7 @@ const ALLOWED_INSTRUMENTATION_NAMES = new Set([ "mistral_ai", "mistralai", "google_genai", + "google_generative_ai", "langchain", "llama_index", "pinecone", diff --git a/src/version.ts b/src/version.ts index 4268add..68b66ac 100644 --- a/src/version.ts +++ b/src/version.ts @@ -1 +1 @@ -export const SDK_VERSION = "1.4.0"; +export const SDK_VERSION = "1.5.0"; From a1930fa9c6a824615245e83d4b5b731e6c425868 Mon Sep 17 00:00:00 2001 From: akash-vijay-kv Date: Wed, 8 Jul 2026 16:52:32 +0530 Subject: [PATCH 5/5] [NET-1321] fix: Solved npm dependency vulnerabilities --- package-lock.json | 4561 ++++++++++++++++++++------------------------- package.json | 44 +- 2 files changed, 2058 insertions(+), 2547 deletions(-) diff --git a/package-lock.json b/package-lock.json index e5d293f..9be9739 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,15 +10,15 @@ "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", + "@opentelemetry/core": "^2.8.0", "@opentelemetry/instrumentation-express": "^0.67.0", "@opentelemetry/instrumentation-http": "^0.219.0", - "@opentelemetry/instrumentation-undici": "^0.6.0", - "@opentelemetry/otlp-transformer": "^0.211.0", - "@opentelemetry/resources": "^2.0.1", - "@opentelemetry/sdk-trace-base": "^2.0.1", - "@traceloop/node-server-sdk": "^0.22.5", - "axios": "^1.13.4", + "@opentelemetry/instrumentation-undici": "^0.10.0", + "@opentelemetry/otlp-transformer": "^0.220.0", + "@opentelemetry/resources": "^2.8.0", + "@opentelemetry/sdk-trace-base": "^2.8.0", + "@traceloop/node-server-sdk": "^0.27.0", + "axios": "^1.18.1", "dotenv": "^17.2.3", "p-limit": "^7.2.0", "shimmer": "^1.2.1" @@ -44,7 +44,7 @@ "@opentelemetry/instrumentation": ">=0.53.0", "@opentelemetry/instrumentation-express": "^0.67.0", "@opentelemetry/instrumentation-http": "^0.219.0", - "@opentelemetry/instrumentation-undici": "^0.6.0", + "@opentelemetry/instrumentation-undici": "^0.10.0", "@prisma/instrumentation": "^5.0.0", "groq-sdk": ">=0.3.0", "openai": "^4.0.0 || ^5.0.0 || ^6.0.0" @@ -108,9 +108,9 @@ } }, "node_modules/@esbuild/aix-ppc64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.27.2.tgz", - "integrity": "sha512-GZMB+a0mOMZs4MpDbj8RJp4cw+w1WV5NYD6xzgvzUJ5Ek2jerwfO2eADyI6ExDSUED+1X8aMbegahsJi+8mgpw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.28.1.tgz", + "integrity": "sha512-Svl7tq8k/08+p6CXPpRjQ1fKX+1odH/BQbb48fV6fj3CWHhsoIOoY87w1oHXm0qEpkIK3ZfVgp0hed3XBXzXMQ==", "cpu": [ "ppc64" ], @@ -125,9 +125,9 @@ } }, "node_modules/@esbuild/android-arm": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.27.2.tgz", - "integrity": "sha512-DVNI8jlPa7Ujbr1yjU2PfUSRtAUZPG9I1RwW4F4xFB1Imiu2on0ADiI/c3td+KmDtVKNbi+nffGDQMfcIMkwIA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.28.1.tgz", + "integrity": "sha512-0k2F129Xdio1TdJfzJ8sy1Q47vUD2NnwdhiAf7drUN1EBTfPf4hsFCtmMgu/6m8JSzsBrlmVjudMBQqOfG8usQ==", "cpu": [ "arm" ], @@ -142,9 +142,9 @@ } }, "node_modules/@esbuild/android-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.27.2.tgz", - "integrity": "sha512-pvz8ZZ7ot/RBphf8fv60ljmaoydPU12VuXHImtAs0XhLLw+EXBi2BLe3OYSBslR4rryHvweW5gmkKFwTiFy6KA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.28.1.tgz", + "integrity": "sha512-34EGEbCIAgosYz6goLcopX6Mo7NyGv9tfwEM2/7Ce2VcVRk568iSvniGWcUXIy7wEDR1wzolcxcriFVrWYcwBg==", "cpu": [ "arm64" ], @@ -159,9 +159,9 @@ } }, "node_modules/@esbuild/android-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.27.2.tgz", - "integrity": "sha512-z8Ank4Byh4TJJOh4wpz8g2vDy75zFL0TlZlkUkEwYXuPSgX8yzep596n6mT7905kA9uHZsf/o2OJZubl2l3M7A==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.28.1.tgz", + "integrity": "sha512-dbwY7ltSMDWsRatcRpCnES4F+im88OCUgGZjy52shC7GqHRE/cYlxNbB4Z4UpJswpcc4Qxd2oE/ufM0p61IKng==", "cpu": [ "x64" ], @@ -176,9 +176,9 @@ } }, "node_modules/@esbuild/darwin-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.27.2.tgz", - "integrity": "sha512-davCD2Zc80nzDVRwXTcQP/28fiJbcOwvdolL0sOiOsbwBa72kegmVU0Wrh1MYrbuCL98Omp5dVhQFWRKR2ZAlg==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.28.1.tgz", + "integrity": "sha512-TZbWkQY7kvTAXbXUT7uVACR5cMHsDiSz9z7ZKAX/RTq/WJEk3QyRr0wZpNhBDX+/0CtdqUIJlOiodQcta6tY3Q==", "cpu": [ "arm64" ], @@ -193,9 +193,9 @@ } }, "node_modules/@esbuild/darwin-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.27.2.tgz", - "integrity": "sha512-ZxtijOmlQCBWGwbVmwOF/UCzuGIbUkqB1faQRf5akQmxRJ1ujusWsb3CVfk/9iZKr2L5SMU5wPBi1UWbvL+VQA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.28.1.tgz", + "integrity": "sha512-zfdzgK9ACBNZLI/CyHTOx81SyNbM6YXn7rxSgX97VjyiPl9W1i4Ka4fgKECEoFCKGpvBj5qArWIGgQjOwkgskQ==", "cpu": [ "x64" ], @@ -210,9 +210,9 @@ } }, "node_modules/@esbuild/freebsd-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.27.2.tgz", - "integrity": "sha512-lS/9CN+rgqQ9czogxlMcBMGd+l8Q3Nj1MFQwBZJyoEKI50XGxwuzznYdwcav6lpOGv5BqaZXqvBSiB/kJ5op+g==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.28.1.tgz", + "integrity": "sha512-wG2EA8ENdEI0qhkSZMjfqrdY+ziCYCPMmtZjjIwOmXFjmyzEHn+UUxk5of+SYsjtfs3VpnlC7QLzSI5hY/rOAw==", "cpu": [ "arm64" ], @@ -227,9 +227,9 @@ } }, "node_modules/@esbuild/freebsd-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.27.2.tgz", - "integrity": "sha512-tAfqtNYb4YgPnJlEFu4c212HYjQWSO/w/h/lQaBK7RbwGIkBOuNKQI9tqWzx7Wtp7bTPaGC6MJvWI608P3wXYA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.28.1.tgz", + "integrity": "sha512-i7dZ9vQgnvSCzi/rYCXNgtF/U+eKZNJBzu3eTQbRgHnM7tNSizLOkRFAl3qzVc/Op/u5YkHHa4pf/3DOYHthLQ==", "cpu": [ "x64" ], @@ -244,9 +244,9 @@ } }, "node_modules/@esbuild/linux-arm": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.27.2.tgz", - "integrity": "sha512-vWfq4GaIMP9AIe4yj1ZUW18RDhx6EPQKjwe7n8BbIecFtCQG4CfHGaHuh7fdfq+y3LIA2vGS/o9ZBGVxIDi9hw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.28.1.tgz", + "integrity": "sha512-qVXBOHQS+d5Y722GwJzJUtOLlX7km3CraOaGormF1pDtPd2C/l1SHRPgjLunLGe51Sh5YYWKMFDyV4SxgMQYTQ==", "cpu": [ "arm" ], @@ -261,9 +261,9 @@ } }, "node_modules/@esbuild/linux-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.27.2.tgz", - "integrity": "sha512-hYxN8pr66NsCCiRFkHUAsxylNOcAQaxSSkHMMjcpx0si13t1LHFphxJZUiGwojB1a/Hd5OiPIqDdXONia6bhTw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.28.1.tgz", + "integrity": "sha512-yHs+0uc8+nvEAfAfxrWQKK5peSNzBc4PegcMO0EJ2hT71uA7vB8Ihg2e77R2P7SG5uYjPbHlLLmve4LLLRCf0g==", "cpu": [ "arm64" ], @@ -278,9 +278,9 @@ } }, "node_modules/@esbuild/linux-ia32": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.27.2.tgz", - "integrity": "sha512-MJt5BRRSScPDwG2hLelYhAAKh9imjHK5+NE/tvnRLbIqUWa+0E9N4WNMjmp/kXXPHZGqPLxggwVhz7QP8CTR8w==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.28.1.tgz", + "integrity": "sha512-d1z4ZuP0ajrfz/FhGT4vv278rX8KnPPJx8i5+AtK7TYbx9Le9F1hyzurZpkEyjkGa9dUGhQow4C1NmeGvqxN2w==", "cpu": [ "ia32" ], @@ -295,9 +295,9 @@ } }, "node_modules/@esbuild/linux-loong64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.27.2.tgz", - "integrity": "sha512-lugyF1atnAT463aO6KPshVCJK5NgRnU4yb3FUumyVz+cGvZbontBgzeGFO1nF+dPueHD367a2ZXe1NtUkAjOtg==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.28.1.tgz", + "integrity": "sha512-M5sRjUVZrkm1OAPR3dlOYzNmN+loZKGVi1VUQGrwuqLcbR6qeAz+famMhjASeH3YVKvZz+zT1jlh/keC3Rj/lg==", "cpu": [ "loong64" ], @@ -312,9 +312,9 @@ } }, "node_modules/@esbuild/linux-mips64el": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.27.2.tgz", - "integrity": "sha512-nlP2I6ArEBewvJ2gjrrkESEZkB5mIoaTswuqNFRv/WYd+ATtUpe9Y09RnJvgvdag7he0OWgEZWhviS1OTOKixw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.28.1.tgz", + "integrity": "sha512-mRObBZeHh2OxcBFPWE/FjylkRgZdYuiTR3vaTozquCGOH14iP9oN4x4Ge81CoIDYQrXmIxpFumJBu5MtZpnQJQ==", "cpu": [ "mips64el" ], @@ -329,9 +329,9 @@ } }, "node_modules/@esbuild/linux-ppc64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.27.2.tgz", - "integrity": "sha512-C92gnpey7tUQONqg1n6dKVbx3vphKtTHJaNG2Ok9lGwbZil6DrfyecMsp9CrmXGQJmZ7iiVXvvZH6Ml5hL6XdQ==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.28.1.tgz", + "integrity": "sha512-slScBsMAb3GFDcdrCgLwZtPYRoH2H/youv10QiZyRjmsP48fznoveWytSgCI/R0ZcUgpc0ZhIUEx6LHts8yrfQ==", "cpu": [ "ppc64" ], @@ -346,9 +346,9 @@ } }, "node_modules/@esbuild/linux-riscv64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.27.2.tgz", - "integrity": "sha512-B5BOmojNtUyN8AXlK0QJyvjEZkWwy/FKvakkTDCziX95AowLZKR6aCDhG7LeF7uMCXEJqwa8Bejz5LTPYm8AvA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.28.1.tgz", + "integrity": "sha512-kw0owk1o0GFETUJyW0jc0G4Yzs0BHZn0JDZ8JRT088vjJYX777BAs1fDGxAC+q831qOs2DTC96mNsG2opdfyyQ==", "cpu": [ "riscv64" ], @@ -363,9 +363,9 @@ } }, "node_modules/@esbuild/linux-s390x": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.27.2.tgz", - "integrity": "sha512-p4bm9+wsPwup5Z8f4EpfN63qNagQ47Ua2znaqGH6bqLlmJ4bx97Y9JdqxgGZ6Y8xVTixUnEkoKSHcpRlDnNr5w==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.28.1.tgz", + "integrity": "sha512-/lAIjX8aYFRByhh6L5rYtPEDRqa9de/4V/juOXcta5frjvzXO4/sqEtyytse0g3zZFuWu5cDN0MkLz2qRDD2Ag==", "cpu": [ "s390x" ], @@ -380,9 +380,9 @@ } }, "node_modules/@esbuild/linux-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.27.2.tgz", - "integrity": "sha512-uwp2Tip5aPmH+NRUwTcfLb+W32WXjpFejTIOWZFw/v7/KnpCDKG66u4DLcurQpiYTiYwQ9B7KOeMJvLCu/OvbA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.28.1.tgz", + "integrity": "sha512-u/anNYF2mmVOEDwLtnQ1wOr3EZ9sTNGLWrsYGYwHWzGA3Si84IOkHXlbWTD1NB+9/1lcnweYKO54uhxZydNzfA==", "cpu": [ "x64" ], @@ -397,9 +397,9 @@ } }, "node_modules/@esbuild/netbsd-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.27.2.tgz", - "integrity": "sha512-Kj6DiBlwXrPsCRDeRvGAUb/LNrBASrfqAIok+xB0LxK8CHqxZ037viF13ugfsIpePH93mX7xfJp97cyDuTZ3cw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-arm64/-/netbsd-arm64-0.28.1.tgz", + "integrity": "sha512-oks0DYbLwWMmaakTsCb+zL4E+aHRVLom9IJZOAthMQEPiQmydXHkziYEsGYRx0uNV/IjEKGAV941JzH02pflqw==", "cpu": [ "arm64" ], @@ -414,9 +414,9 @@ } }, "node_modules/@esbuild/netbsd-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.27.2.tgz", - "integrity": "sha512-HwGDZ0VLVBY3Y+Nw0JexZy9o/nUAWq9MlV7cahpaXKW6TOzfVno3y3/M8Ga8u8Yr7GldLOov27xiCnqRZf0tCA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.28.1.tgz", + "integrity": "sha512-aeL6lAnN89Hz43Mlh1G8ARasbuoYvSITDEx0tHh5b7jJnHcssqgjy9Yx430GDpmCa6OyrKoS0aNRjKundRizGg==", "cpu": [ "x64" ], @@ -431,9 +431,9 @@ } }, "node_modules/@esbuild/openbsd-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.27.2.tgz", - "integrity": "sha512-DNIHH2BPQ5551A7oSHD0CKbwIA/Ox7+78/AWkbS5QoRzaqlev2uFayfSxq68EkonB+IKjiuxBFoV8ESJy8bOHA==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-arm64/-/openbsd-arm64-0.28.1.tgz", + "integrity": "sha512-MEFJe5C3R8pwXdZ5Y21oo6m7ePiS0d9pWucn99O/wvyJZChoIQKrQDxKrGeW8F5+T0okTHesAmDeiHDTIq0V/Q==", "cpu": [ "arm64" ], @@ -448,9 +448,9 @@ } }, "node_modules/@esbuild/openbsd-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.27.2.tgz", - "integrity": "sha512-/it7w9Nb7+0KFIzjalNJVR5bOzA9Vay+yIPLVHfIQYG/j+j9VTH84aNB8ExGKPU4AzfaEvN9/V4HV+F+vo8OEg==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.28.1.tgz", + "integrity": "sha512-i/ZLIOafE0Z8cI/XANJAixoJL/uRAoS2xOA3rb0xN+KK0K177cMAsQYkzHtBrtMXAKuAc7HGgcWiZ/sRC1Nxgw==", "cpu": [ "x64" ], @@ -465,9 +465,9 @@ } }, "node_modules/@esbuild/openharmony-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.27.2.tgz", - "integrity": "sha512-LRBbCmiU51IXfeXk59csuX/aSaToeG7w48nMwA6049Y4J4+VbWALAuXcs+qcD04rHDuSCSRKdmY63sruDS5qag==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/openharmony-arm64/-/openharmony-arm64-0.28.1.tgz", + "integrity": "sha512-ge+Z7EXFNt2BO1oAMsVpiQ8EwndV9i1xXerAeTIK7AtPs3bKFXQM7nlRxDSIUIMeueR1CNXxqztLzdNeReKBJg==", "cpu": [ "arm64" ], @@ -482,9 +482,9 @@ } }, "node_modules/@esbuild/sunos-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.27.2.tgz", - "integrity": "sha512-kMtx1yqJHTmqaqHPAzKCAkDaKsffmXkPHThSfRwZGyuqyIeBvf08KSsYXl+abf5HDAPMJIPnbBfXvP2ZC2TfHg==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.28.1.tgz", + "integrity": "sha512-BEjgtECkL3vY+SaSQ6nzVfiALUeFxpawyp8Jmf5PtYhf1Ug40N1h/hxlhts+f1FvSvarEigdxS3BlSMI2PJLcQ==", "cpu": [ "x64" ], @@ -499,9 +499,9 @@ } }, "node_modules/@esbuild/win32-arm64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.27.2.tgz", - "integrity": "sha512-Yaf78O/B3Kkh+nKABUF++bvJv5Ijoy9AN1ww904rOXZFLWVc5OLOfL56W+C8F9xn5JQZa3UX6m+IktJnIb1Jjg==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.28.1.tgz", + "integrity": "sha512-lCv9eK/H6ZJWbE7bh2nw54CZ9M2nupBxJcTsdk/QQnWkdSjKGuxmmH8/GWrlT1eMmZfn4dGcCjRte397WqfQXA==", "cpu": [ "arm64" ], @@ -516,9 +516,9 @@ } }, "node_modules/@esbuild/win32-ia32": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.27.2.tgz", - "integrity": "sha512-Iuws0kxo4yusk7sw70Xa2E2imZU5HoixzxfGCdxwBdhiDgt9vX9VUCBhqcwY7/uh//78A1hMkkROMJq9l27oLQ==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.28.1.tgz", + "integrity": "sha512-zvb/mB2bSCoJOpoCBgYKKpX6YM6mJBlBUVUtVj41DlZJVEB6/0CKlRYxP5wWl1C1ILiCoAU5wZZ4q1P3qeS6Eg==", "cpu": [ "ia32" ], @@ -533,9 +533,9 @@ } }, "node_modules/@esbuild/win32-x64": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.27.2.tgz", - "integrity": "sha512-sRdU18mcKf7F+YgheI/zGf5alZatMUTKj/jNS6l744f9u3WFu4v7twcUI9vu4mknF4Y9aDlblIie0IM+5xxaqQ==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.28.1.tgz", + "integrity": "sha512-bm4Mowrv+GXMlpWX++EcXw/iLyd1o3+bJkC2DkWXYVvgZCqD/bSj9ctZeAMC3cIxgjRVR2Dufaiu4YPxr5gW1A==", "cpu": [ "x64" ], @@ -588,9 +588,9 @@ } }, "node_modules/@grpc/grpc-js": { - "version": "1.14.3", - "resolved": "https://registry.npmjs.org/@grpc/grpc-js/-/grpc-js-1.14.3.tgz", - "integrity": "sha512-Iq8QQQ/7X3Sac15oB6p0FmUg/klxQvXLeileoqrTRGJYLV+/9tubbr9ipz0GKHjmXVsgFPo/+W+2cA8eNcR+XA==", + "version": "1.14.4", + "resolved": "https://registry.npmjs.org/@grpc/grpc-js/-/grpc-js-1.14.4.tgz", + "integrity": "sha512-k9Dj3DV/itK9D06Y8f190Qgop7/Ui+D0njFV3LHMPwPT75DpXLQohE9Wmz0QElrJnzsjB7KPWiKJbOl7IPDArQ==", "license": "Apache-2.0", "dependencies": { "@grpc/proto-loader": "^0.8.0", @@ -601,14 +601,14 @@ } }, "node_modules/@grpc/proto-loader": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/@grpc/proto-loader/-/proto-loader-0.8.0.tgz", - "integrity": "sha512-rc1hOQtjIWGxcxpb9aHAfLpIctjEnsDehj0DAiVfBlmT84uvR0uUtN2hEi/ecvWVjXUGf5qPF4qEgiLOx1YIMQ==", + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/@grpc/proto-loader/-/proto-loader-0.8.1.tgz", + "integrity": "sha512-wtF6h+DY6M3YaDBPAmvuuA6jV8Sif9MjtOI5euKFWRgCDl5PeDpPsHR9u2l6St5ceY8AZgoNDww5+HvEsXFsGg==", "license": "Apache-2.0", "dependencies": { "lodash.camelcase": "^4.3.0", "long": "^5.0.0", - "protobufjs": "^7.5.3", + "protobufjs": "^7.5.5", "yargs": "^17.7.2" }, "bin": { @@ -679,21 +679,17 @@ } }, "node_modules/@langchain/core": { - "version": "1.1.16", - "resolved": "https://registry.npmjs.org/@langchain/core/-/core-1.1.16.tgz", - "integrity": "sha512-2XKQKxvQdeQiuIo0tacAmDVojhSVAci8D2WDdmmyN+6CqDusLHEHyIDaOt4o+UBvpkyHXbCdrljzDTQY/AKeqg==", + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@langchain/core/-/core-1.2.1.tgz", + "integrity": "sha512-NNG/cC5FGuHDOAP56h0ddp8Rfk8p+othWzEK5RV9JIG6RvnF5vGa5r0AEGtKfQieed7s1kC42GuIzVOBvMBL/g==", "license": "MIT", - "peer": true, "dependencies": { "@cfworker/json-schema": "^4.0.2", - "ansi-styles": "^5.0.0", - "camelcase": "6", - "decamelize": "1.2.0", + "@standard-schema/spec": "^1.1.0", "js-tiktoken": "^1.0.12", - "langsmith": ">=0.4.0 <1.0.0", + "langsmith": ">=0.5.0 <1.0.0", "mustache": "^4.2.0", "p-queue": "^6.6.2", - "uuid": "^10.0.0", "zod": "^3.25.76 || ^4" }, "engines": { @@ -701,71 +697,69 @@ } }, "node_modules/@langchain/langgraph": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/@langchain/langgraph/-/langgraph-1.1.1.tgz", - "integrity": "sha512-FfFiaUwc2P5cy0AyALTA72S9OuutBLy+TRQECQSkwI5H40UNF+h7HM0U28xGTfmQ6MrqzbnnpRfXRTQX4jqsUw==", + "version": "1.4.7", + "resolved": "https://registry.npmjs.org/@langchain/langgraph/-/langgraph-1.4.7.tgz", + "integrity": "sha512-2tcyf3QGC7v89kqSxMCtRvzg/3L/4yHtOaWC49A8KieCciWJs7LGaxHoPB6QRxXyUgyR+Zg9Q1ss/XJIE+JuSQ==", "license": "MIT", "peer": true, "dependencies": { - "@langchain/langgraph-checkpoint": "^1.0.0", - "@langchain/langgraph-sdk": "~1.5.5", - "uuid": "^10.0.0" + "@langchain/langgraph-checkpoint": "^1.1.3", + "@langchain/langgraph-sdk": "~1.9.25", + "@langchain/protocol": "^0.0.18", + "@standard-schema/spec": "1.1.0" }, "engines": { "node": ">=18" }, "peerDependencies": { - "@langchain/core": "^1.0.1", - "zod": "^3.25.32 || ^4.2.0", - "zod-to-json-schema": "^3.x" - }, - "peerDependenciesMeta": { - "zod-to-json-schema": { - "optional": true - } + "@langchain/core": "^1.1.48", + "zod": "^3.25.32 || ^4.2.0" } }, "node_modules/@langchain/langgraph-checkpoint": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/@langchain/langgraph-checkpoint/-/langgraph-checkpoint-1.0.0.tgz", - "integrity": "sha512-xrclBGvNCXDmi0Nz28t3vjpxSH6UYx6w5XAXSiiB1WEdc2xD2iY/a913I3x3a31XpInUW/GGfXXfePfaghV54A==", + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@langchain/langgraph-checkpoint/-/langgraph-checkpoint-1.1.3.tgz", + "integrity": "sha512-wgzdQNeEsdw1e+4lvlj0tdq/RYR/k1vPin10g0ymGoehZDDgd9nvIllGXSXN4TFgF9sf5qQP/KTkOcLfeseIhA==", "license": "MIT", "peer": true, - "dependencies": { - "uuid": "^10.0.0" - }, "engines": { "node": ">=18" }, "peerDependencies": { - "@langchain/core": "^1.0.1" + "@langchain/core": "^1.1.48" } }, "node_modules/@langchain/langgraph-sdk": { - "version": "1.5.5", - "resolved": "https://registry.npmjs.org/@langchain/langgraph-sdk/-/langgraph-sdk-1.5.5.tgz", - "integrity": "sha512-SyiAs6TVXPWlt/8cI9pj/43nbIvclY3ytKqUFbL5MplCUnItetEyqvH87EncxyVF5D7iJKRZRfSVYBMmOZbjbQ==", + "version": "1.9.25", + "resolved": "https://registry.npmjs.org/@langchain/langgraph-sdk/-/langgraph-sdk-1.9.25.tgz", + "integrity": "sha512-mRKW8zyQUaHox+HirRFMRrPqOvNbQI3xeXDt6kkk4PbBg77V92bsO1WzUVNrmJ81zCkvxyOrWSK8D6ioCj0a8A==", "license": "MIT", "peer": true, "dependencies": { + "@langchain/protocol": "^0.0.18", + "@types/json-schema": "^7.0.15", "p-queue": "^9.0.1", - "p-retry": "^7.1.1", - "uuid": "^13.0.0" + "p-retry": "^7.1.1" }, "peerDependencies": { - "@langchain/core": "^1.1.15", + "@langchain/core": "^1.1.48", "react": "^18 || ^19", - "react-dom": "^18 || ^19" + "react-dom": "^18 || ^19", + "svelte": "^4.0.0 || ^5.0.0", + "vue": "^3.0.0" }, "peerDependenciesMeta": { - "@langchain/core": { - "optional": true - }, "react": { "optional": true }, "react-dom": { "optional": true + }, + "svelte": { + "optional": true + }, + "vue": { + "optional": true } } }, @@ -777,13 +771,13 @@ "peer": true }, "node_modules/@langchain/langgraph-sdk/node_modules/p-queue": { - "version": "9.1.0", - "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-9.1.0.tgz", - "integrity": "sha512-O/ZPaXuQV29uSLbxWBGGZO1mCQXV2BLIwUr59JUU9SoH76mnYvtms7aafH/isNSNGwuEfP6W/4xD0/TJXxrizw==", + "version": "9.3.1", + "resolved": "https://registry.npmjs.org/p-queue/-/p-queue-9.3.1.tgz", + "integrity": "sha512-POWdiIPmsUPGwb4FeQ4OBg46aqmcInSWe45CKDsGHiOBiVQM9chqfQTuqhuTzcg2Vz9faTI65at0KkVyVEiCHw==", "license": "MIT", "peer": true, "dependencies": { - "eventemitter3": "^5.0.1", + "eventemitter3": "^5.0.4", "p-timeout": "^7.0.0" }, "engines": { @@ -806,29 +800,14 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/@langchain/langgraph-sdk/node_modules/uuid": { - "version": "13.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-13.0.0.tgz", - "integrity": "sha512-XQegIaBTVUjSHliKqcnFqYypAd4S+WCYt5NIeRs6w/UAry7z8Y9j5ZwRRL4kzq9U3sD6v+85er9FvkEaBpji2w==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "peer": true, - "bin": { - "uuid": "dist-node/bin/uuid" - } - }, "node_modules/@langchain/ollama": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/@langchain/ollama/-/ollama-1.2.1.tgz", - "integrity": "sha512-qtgPC2jD/7cIb2DgeDafK4MgiQS3b8K0bsBUn87hel0b8lKQPSzKlAv2P/8jsJw12OvD0Vz7yKSj9TTuyMmV4w==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/@langchain/ollama/-/ollama-1.3.0.tgz", + "integrity": "sha512-uzLkZVTXN0SI5zAoJbJzL4y/QN7gbmJ1txBgFfqJ5M0Qf+Yu2Zu8q98L3jIrfM+akWMaNmRU4R4APhcfQmeIsw==", "license": "MIT", "peer": true, "dependencies": { - "ollama": "^0.6.3", - "uuid": "^10.0.0" + "ollama": "^0.6.3" }, "engines": { "node": ">=20" @@ -837,19 +816,26 @@ "@langchain/core": "^1.0.0" } }, + "node_modules/@langchain/protocol": { + "version": "0.0.18", + "resolved": "https://registry.npmjs.org/@langchain/protocol/-/protocol-0.0.18.tgz", + "integrity": "sha512-XW1egQtPfsGI41w2AMZNFZrUIwFSQHTjVMZs0OaTpCAvht/QLoaPN8FQcsysMVypOhupG28J29yOorrc70otBQ==", + "license": "MIT", + "peer": true + }, "node_modules/@opentelemetry/api": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.0.tgz", - "integrity": "sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==", + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/api/-/api-1.9.1.tgz", + "integrity": "sha512-gLyJlPHPZYdAk1JENA9LeHejZe1Ti77/pTeFm/nMXmQH/HFZlcS/O2XJB+L8fkbrNSqhdtlvjBVjxwUYanNH5Q==", "license": "Apache-2.0", "engines": { "node": ">=8.0.0" } }, "node_modules/@opentelemetry/api-logs": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", - "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "version": "0.219.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.219.0.tgz", + "integrity": "sha512-FFx7YnaYJlIjqWW/AG/yAZ0L/NEY724PipXXXQLdtZPbLwBGbUMTGL1i/esI56TWfTUXxhLfpgrnWJCG8aUJyg==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.3.0" @@ -858,10 +844,26 @@ "node": ">=8.0.0" } }, + "node_modules/@opentelemetry/configuration": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/configuration/-/configuration-0.220.0.tgz", + "integrity": "sha512-glfIVKnZevRin8fY/9uES/mhRtMT1lGINLHc9MIo5fTQZXswEEHamJtgjv4MTtzgnhHGC92mIS/0lzAUZMyE0w==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/core": "2.9.0", + "yaml": "^2.8.3" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.9.0" + } + }, "node_modules/@opentelemetry/context-async-hooks": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-2.4.0.tgz", - "integrity": "sha512-jn0phJ+hU7ZuvaoZE/8/Euw3gvHJrn2yi+kXrymwObEPVPjtwCmkvXDRQCWli+fCTTF/aSOtXaLr7CLIvv3LQg==", + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-2.9.0.tgz", + "integrity": "sha512-OQ0vzvbZBiUhjqLnUaoNfYmP8553Crr3aggB4y0ZUi815mZ7idpdJXQmoKdeBKJelYttoBlLSSHubmyw3wvX4w==", "license": "Apache-2.0", "engines": { "node": "^18.19.0 || >=20.6.0" @@ -871,9 +873,9 @@ } }, "node_modules/@opentelemetry/core": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.4.0.tgz", - "integrity": "sha512-KtcyFHssTn5ZgDu6SXmUznS80OFs/wN7y6MyFRRcKU6TOw8hNcGxKvt8hsdaLJfhzUszNSjURetq5Qpkad14Gw==", + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.9.0.tgz", + "integrity": "sha512-m2nckMT80NnmjTYSPjJQObBJ+8dgkoajEOUbznL8AHZ3T3yHRk2P7gI1PhEBc1+lOnrYE9UWrWHqJDsmqjmNbw==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/semantic-conventions": "^1.29.0" @@ -886,17 +888,17 @@ } }, "node_modules/@opentelemetry/exporter-logs-otlp-grpc": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-grpc/-/exporter-logs-otlp-grpc-0.203.0.tgz", - "integrity": "sha512-g/2Y2noc/l96zmM+g0LdeuyYKINyBwN6FJySoU15LHPLcMN/1a0wNk2SegwKcxrRdE7Xsm7fkIR5n6XFe3QpPw==", + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-grpc/-/exporter-logs-otlp-grpc-0.220.0.tgz", + "integrity": "sha512-s0sRPCSlXYqlgObOpCftomJllp3LfUL9FobQ5csg2172ydVhSEnu1ptpsVBJadazs5nUNp7vDuLE03FAFWTLOQ==", "license": "Apache-2.0", "dependencies": { - "@grpc/grpc-js": "^1.7.1", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-grpc-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/sdk-logs": "0.203.0" + "@grpc/grpc-js": "^1.14.3", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/sdk-logs": "0.220.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -905,86 +907,87 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-grpc/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/exporter-logs-otlp-http": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-http/-/exporter-logs-otlp-http-0.220.0.tgz", + "integrity": "sha512-8186thl+pTw64iz/qEEen5oJZoZ/gO73XruChdaGlYdWOdBIQ42r+vHLf6a7vIDqTD4b8ZOoMlyxptanECaI9A==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api-logs": "0.220.0", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/sdk-logs": "0.220.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-grpc/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/api-logs": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.220.0.tgz", + "integrity": "sha512-CmVa4ImJ+ynfrPMNaAXHET6Bhb44SwzmfyVJFq9ni2jgXJR/l7C6gfVFddNmHP+ZOkP9cf4f9DBe68qVLTHc9w==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-grpc/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/exporter-logs-otlp-proto": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-proto/-/exporter-logs-otlp-proto-0.220.0.tgz", + "integrity": "sha512-8LZAxdJ0ENDAFwr4j0oY35mHBltiSzvlhdQAPGiC7p9VnxtuSq4SW1gfBAdW6t6hiQG6OwUl8w7KHaOdJPKHWg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/sdk-logs": "0.220.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-grpc/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/exporter-metrics-otlp-grpc": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-grpc/-/exporter-metrics-otlp-grpc-0.220.0.tgz", + "integrity": "sha512-U128izvJfX/dW9jRGP0gIfadR1Hg7ft3UEGIeRxLFK70m2BWw6AtNCOnsUygpw2zCgR/ygdWbGpcL6TmhW0ZGw==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@grpc/grpc-js": "^1.14.3", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.220.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-metrics": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-http": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-http/-/exporter-logs-otlp-http-0.203.0.tgz", - "integrity": "sha512-s0hys1ljqlMTbXx2XiplmMJg9wG570Z5lH7wMvrZX6lcODI56sG4HL03jklF63tBeyNwK2RV1/ntXGo3HgG4Qw==", + "node_modules/@opentelemetry/exporter-metrics-otlp-http": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-http/-/exporter-metrics-otlp-http-0.220.0.tgz", + "integrity": "sha512-Yqt3RBw/bRVncaE9qIIhk4WfjbAQqXuP9FgAaU+IKPndnLEp/cUqZlSC324+bpmduRz7DoTjig8Ub0PeILWXUA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/sdk-logs": "0.203.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-metrics": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -993,34 +996,36 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/exporter-metrics-otlp-proto": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-proto/-/exporter-metrics-otlp-proto-0.220.0.tgz", + "integrity": "sha512-lyO+IQBdSvqHN/ZOW/OzrSWemtfD+HgWngn+HBNLhjy0YrCQQTz0OE/kSekH2Pl340dn9DWzhqHdz5Eftr+HLA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.220.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-metrics": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/exporter-prometheus": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-prometheus/-/exporter-prometheus-0.220.0.tgz", + "integrity": "sha512-JZD5DL/NBpVd2BHefvYosm3G40UZ/KzExLv5tc0eZe0CtrsHHtcOk3YPUxR2EINmUeBf8+w5UReTV8fFPn95lA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-metrics": "2.9.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1029,52 +1034,55 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/exporter-trace-otlp-grpc": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-grpc/-/exporter-trace-otlp-grpc-0.220.0.tgz", + "integrity": "sha512-bv1xmNhmNwIM6MdUBw4yYuJeVcEViVLk3uD69vOQMwueHBnfyl/u0HnBlB1FNY/Te0UOzJzvcbyR8wN6b+iGbA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@grpc/grpc-js": "^1.14.3", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/sdk-trace": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-http/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/exporter-trace-otlp-http": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-http/-/exporter-trace-otlp-http-0.220.0.tgz", + "integrity": "sha512-/+ExB3lRkf+erv4PnoywyL7RHKITidxtUpUTS55k7OQ0dB42S7gEF1gry7swb9MSm1hYLUhJg4QQh9W8SpwwqA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-proto": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-logs-otlp-proto/-/exporter-logs-otlp-proto-0.203.0.tgz", - "integrity": "sha512-nl/7S91MXn5R1aIzoWtMKGvqxgJgepB/sH9qW0rZvZtabnsjbf8OQ1uSx3yogtvLr0GzwD596nQKz2fV7q2RBw==", + "node_modules/@opentelemetry/exporter-trace-otlp-proto": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-proto/-/exporter-trace-otlp-proto-0.220.0.tgz", + "integrity": "sha512-voTAD8XgJxlK7zLkXh8EzMB09zrQr3tyY/BsnDTlDiQU/UdK58MZ63A3mUjdEDrxMjCVmBHU3WQJhRmQe+Dvzg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-trace-base": "2.0.1" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1083,34 +1091,33 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/exporter-zipkin": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-zipkin/-/exporter-zipkin-2.9.0.tgz", + "integrity": "sha512-RwINoce2BH8T4obT5pMcAla2sWma1YZvYuaktWmTluQ0PkQdvv5D060rWI1+kawX+J2qBRcMbwrZJJNcMJUauQ==", "license": "Apache-2.0", "dependencies": { + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.0.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/instrumentation": { + "version": "0.219.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.219.0.tgz", + "integrity": "sha512-X5t7I8GyIO9rmGHwoedZLREpQqrF1WW2nxzNNym6HOKpFiE+rvqV3ngC0xcZVO2YwIGf3KKmRdWrYwdwz3H9RQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api-logs": "0.219.0", + "import-in-the-middle": "^3.0.0", + "require-in-the-middle": "^8.0.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1119,141 +1126,147 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/instrumentation-express": { + "version": "0.67.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-express/-/instrumentation-express-0.67.0.tgz", + "integrity": "sha512-1WTWX2YNZIV+jPmEqdf/Vd1gHMT92TKA/0pf/iIItWhV6+RhzhnUUW4kSWQn8L3qVcgWEzQ860/ZOwaIwayi8A==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "^2.0.0", + "@opentelemetry/instrumentation": "^0.219.0", + "@opentelemetry/semantic-conventions": "^1.27.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-logs-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/instrumentation-http": { + "version": "0.219.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-http/-/instrumentation-http-0.219.0.tgz", + "integrity": "sha512-nNt1fqpyah/OKjNHdEOu8xLwISppRU2qJuF8aR+fCcftVwdFkPgtworBLA+TI1HU2iF508jcQBF2gerWczJAXg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.8.0", + "@opentelemetry/instrumentation": "0.219.0", + "@opentelemetry/semantic-conventions": "^1.29.0", + "forwarded-parse": "2.1.2" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-grpc": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-grpc/-/exporter-metrics-otlp-grpc-0.203.0.tgz", - "integrity": "sha512-FCCj9nVZpumPQSEI57jRAA89hQQgONuoC35Lt+rayWY/mzCAc6BQT7RFyFaZKJ2B7IQ8kYjOCPsF/HGFWjdQkQ==", + "node_modules/@opentelemetry/instrumentation-undici": { + "version": "0.10.1", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-undici/-/instrumentation-undici-0.10.1.tgz", + "integrity": "sha512-rkOGikPEyRpMCmNu9AQuV5dtRlDmJp2dK5sw8roVshAGoB6hH/3QjDtRhdwd75SsJwgynWUNRUYe0wAkTo16tQ==", "license": "Apache-2.0", "dependencies": { - "@grpc/grpc-js": "^1.7.1", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/exporter-metrics-otlp-http": "0.203.0", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-grpc-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-metrics": "2.0.1" + "@opentelemetry/core": "^1.8.0", + "@opentelemetry/instrumentation": "^0.57.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" + "node": ">=14" }, "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "@opentelemetry/api": "^1.7.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-grpc/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/api-logs": { + "version": "0.57.2", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.57.2.tgz", + "integrity": "sha512-uIX52NnTM0iBh84MShlpouI7UKqkZ7MrUszTmaypHBu4r7NofznSnQRfJ+uUeDtQDj6w8eFGg5KBLDAwAPz1+A==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-grpc/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/instrumentation": { + "version": "0.57.2", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.57.2.tgz", + "integrity": "sha512-BdBGhQBh8IjZ2oIIX6F2/Q3LKm/FDDKi6ccYKcBTeilh6SNdNKveDOLk73BkSJjQLJk6qe4Yh+hHw1UPhCDdrg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api-logs": "0.57.2", + "@types/shimmer": "^1.2.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1", + "semver": "^7.5.2", + "shimmer": "^1.2.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" + "node": ">=14" }, "peerDependencies": { "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-grpc/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/instrumentation-undici/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@opentelemetry/instrumentation-undici/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@opentelemetry/instrumentation-undici/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-grpc/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/otlp-exporter-base": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.220.0.tgz", + "integrity": "sha512-CXYo8UD5Mn9YbgebO2EL4wejtA+gxLmLiu6HCk2KH2BR7XhFN6/6p1UlCb23DYCjeYkndevLHuejCCN1yx4+OQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-transformer": "0.220.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-http": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-http/-/exporter-metrics-otlp-http-0.203.0.tgz", - "integrity": "sha512-HFSW10y8lY6BTZecGNpV3GpoSy7eaO0Z6GATwZasnT4bEsILp8UJXNG5OmEsz4SdwCSYvyCbTJdNbZP3/8LGCQ==", + "node_modules/@opentelemetry/otlp-grpc-exporter-base": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-grpc-exporter-base/-/otlp-grpc-exporter-base-0.220.0.tgz", + "integrity": "sha512-/eIkBPMBTIvM3x/0mDX4aJeSkYifYClnBPr68PL1h5LV4VQv4+SV6CGrpiZ4fIWDnobVmhTWCm1J/QRdAWUfvA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-metrics": "2.0.1" + "@grpc/grpc-js": "^1.14.3", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-transformer": "0.220.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1262,155 +1275,162 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/otlp-transformer": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.220.0.tgz", + "integrity": "sha512-lXGrv7KXZ0gNH9SVNUaa6vv6phVYGvJxfXAlMbzbakiXru75f5MZl8Z7oqiMMQD77riVHJCFlQvbZs/VVN2/4A==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api-logs": "0.220.0", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-logs": "0.220.0", + "@opentelemetry/sdk-metrics": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/api-logs": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.220.0.tgz", + "integrity": "sha512-CmVa4ImJ+ynfrPMNaAXHET6Bhb44SwzmfyVJFq9ni2jgXJR/l7C6gfVFddNmHP+ZOkP9cf4f9DBe68qVLTHc9w==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/propagator-b3": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-b3/-/propagator-b3-2.9.0.tgz", + "integrity": "sha512-WrOT1WsOUG+B7hstD2RYoMPIOK76G8E9AQHhMjUvrQaGx/oA7rPWQvvr1Rqv7+yy4R0ZMVwWLC4vW2xnkgWPAQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-http/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/propagator-jaeger": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-jaeger/-/propagator-jaeger-2.9.0.tgz", + "integrity": "sha512-4mYGty27rYvSM0jtp1ZUOqd3LfVRCYg9H5G9OFzSx5HViYToU21MFhWfco7x1HwXr7ER8yGOiCIHZUwjPksc0Q==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-proto": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-metrics-otlp-proto/-/exporter-metrics-otlp-proto-0.203.0.tgz", - "integrity": "sha512-OZnhyd9npU7QbyuHXFEPVm3LnjZYifuKpT3kTnF84mXeEQ84pJJZgyLBpU4FSkSwUkt/zbMyNAI7y5+jYTWGIg==", + "node_modules/@opentelemetry/resources": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.9.0.tgz", + "integrity": "sha512-jyA5MBLQ+Dkl3+JsZkUoUvL7yHvU64kLsvpXKarWm6347Sl1t1bXFTFykUePNpT5WH5pm9a2Qtt03iIYQhZ1Fg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/exporter-metrics-otlp-http": "0.203.0", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-metrics": "2.0.1" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/sdk-logs": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.220.0.tgz", + "integrity": "sha512-WywcTkQtv2iNmt+6y5Kcd4rzvx9bLVsBa2Nwcmg01IUaBTkTow3W4d9KE5vNBpEDtb9tp21WcRBY/lANRrApYA==", "license": "Apache-2.0", "dependencies": { + "@opentelemetry/api-logs": "0.220.0", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": ">=1.4.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/sdk-logs/node_modules/@opentelemetry/api-logs": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.220.0.tgz", + "integrity": "sha512-CmVa4ImJ+ynfrPMNaAXHET6Bhb44SwzmfyVJFq9ni2jgXJR/l7C6gfVFddNmHP+ZOkP9cf4f9DBe68qVLTHc9w==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/sdk-metrics": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.9.0.tgz", + "integrity": "sha512-Xx8RGS4H5XEBl01WuCreMIpiah9cCXMbSkeuIePPdD2cUpq/vUzYmj8E/MK1OsbOc93FuAD4jfn2WOacKwLn7Q==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@opentelemetry/api": ">=1.9.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-metrics-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", + "node_modules/@opentelemetry/sdk-node": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-node/-/sdk-node-0.220.0.tgz", + "integrity": "sha512-wHtGyHhSKHNH3fym33xRu4Ef/HXTFvX8eQ42xdQdEO9LYx9Y2qNyBDJytyqVlvmo6abWZlNYTUthuAGUMYqYnQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.220.0", + "@opentelemetry/configuration": "0.220.0", + "@opentelemetry/context-async-hooks": "2.9.0", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/exporter-logs-otlp-grpc": "0.220.0", + "@opentelemetry/exporter-logs-otlp-http": "0.220.0", + "@opentelemetry/exporter-logs-otlp-proto": "0.220.0", + "@opentelemetry/exporter-metrics-otlp-grpc": "0.220.0", + "@opentelemetry/exporter-metrics-otlp-http": "0.220.0", + "@opentelemetry/exporter-metrics-otlp-proto": "0.220.0", + "@opentelemetry/exporter-prometheus": "0.220.0", + "@opentelemetry/exporter-trace-otlp-grpc": "0.220.0", + "@opentelemetry/exporter-trace-otlp-http": "0.220.0", + "@opentelemetry/exporter-trace-otlp-proto": "0.220.0", + "@opentelemetry/exporter-zipkin": "2.9.0", + "@opentelemetry/instrumentation": "0.220.0", + "@opentelemetry/otlp-exporter-base": "0.220.0", + "@opentelemetry/otlp-grpc-exporter-base": "0.220.0", + "@opentelemetry/propagator-b3": "2.9.0", + "@opentelemetry/propagator-jaeger": "2.9.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-logs": "0.220.0", + "@opentelemetry/sdk-metrics": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0", + "@opentelemetry/sdk-trace-base": "2.9.0", + "@opentelemetry/sdk-trace-node": "2.9.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { @@ -1420,103 +1440,27 @@ "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-prometheus": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-prometheus/-/exporter-prometheus-0.203.0.tgz", - "integrity": "sha512-2jLuNuw5m4sUj/SncDf/mFPabUxMZmmYetx5RKIMIQyPnl6G6ooFzfeE8aXNRf8YD1ZXNlCnRPcISxjveGJHNg==", + "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/api-logs": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.220.0.tgz", + "integrity": "sha512-CmVa4ImJ+ynfrPMNaAXHET6Bhb44SwzmfyVJFq9ni2jgXJR/l7C6gfVFddNmHP+ZOkP9cf4f9DBe68qVLTHc9w==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-metrics": "2.0.1" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/exporter-prometheus/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } - }, - "node_modules/@opentelemetry/exporter-prometheus/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } - }, - "node_modules/@opentelemetry/exporter-trace-otlp-grpc": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-grpc/-/exporter-trace-otlp-grpc-0.203.0.tgz", - "integrity": "sha512-322coOTf81bm6cAA8+ML6A+m4r2xTCdmAZzGNTboPXRzhwPt4JEmovsFAs+grpdarObd68msOJ9FfH3jxM6wqA==", - "license": "Apache-2.0", - "dependencies": { - "@grpc/grpc-js": "^1.7.1", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-grpc-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/exporter-trace-otlp-grpc/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-grpc/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", + "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/instrumentation": { + "version": "0.220.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.220.0.tgz", + "integrity": "sha512-xQx3E2WxP1mDvKzxLxX+CTCtNLa560YJZ3087qYHerl2YmiKpv7AH+dAy7vmx+eVrZ5BwhfWUAVoKOoxCNHcpw==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" + "@opentelemetry/api-logs": "0.220.0", + "import-in-the-middle": "^3.0.0", + "require-in-the-middle": "^8.0.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1525,13 +1469,14 @@ "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-grpc/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/sdk-trace": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace/-/sdk-trace-2.9.0.tgz", + "integrity": "sha512-sGA19HvtrrSKYsseHphluH6j3p6Xa3fqc7c7y8f/7mYWejc1lyDFcpSdD1kYa50HCLUeEo4zA5bW0pniaPszuw==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { @@ -1541,14 +1486,15 @@ "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-grpc/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@opentelemetry/sdk-trace-base": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.9.0.tgz", + "integrity": "sha512-cp9zmTl62R8PJrpvFcmc8N2JQU/xfa0S+61q511Nji+QxCfZ8Ifvg7H27G8cANe4crg4RTrWsVvanHiXjSp6ag==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/resources": "2.9.0", + "@opentelemetry/sdk-trace": "2.9.0", "@opentelemetry/semantic-conventions": "^1.29.0" }, "engines": { @@ -1558,32 +1504,15 @@ "@opentelemetry/api": ">=1.3.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-http": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-http/-/exporter-trace-otlp-http-0.203.0.tgz", - "integrity": "sha512-ZDiaswNYo0yq/cy1bBLJFe691izEJ6IgNmkjm4C6kE9ub/OMQqDXORx2D2j8fzTBTxONyzusbaZlqtfmyqURPw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/exporter-trace-otlp-http/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@opentelemetry/sdk-trace-node": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-2.9.0.tgz", + "integrity": "sha512-ec9a7ps37huy5itYk0MalaZdSLlM6AXWp/FhtEjgMpp5leEGojBDvAl/UWttQnkMZOvFHKzRESn8TD3yKTF5nQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/context-async-hooks": "2.9.0", + "@opentelemetry/core": "2.9.0", + "@opentelemetry/sdk-trace-base": "2.9.0" }, "engines": { "node": "^18.19.0 || >=20.6.0" @@ -1592,676 +1521,472 @@ "@opentelemetry/api": ">=1.0.0 <1.10.0" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-http/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/exporter-trace-otlp-http/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@opentelemetry/semantic-conventions": { + "version": "1.42.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.42.0.tgz", + "integrity": "sha512-icc5xCzndZfhuJMy5oqk5AvloWquR7jtae74qzpkKkhGp8BivK+oCcEXgGnjCdTfp8hA44l+w8gE8yYJbocJJw==", "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-http/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@protobufjs/aspromise": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/aspromise/-/aspromise-1.1.2.tgz", + "integrity": "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-trace-otlp-proto": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-trace-otlp-proto/-/exporter-trace-otlp-proto-0.203.0.tgz", - "integrity": "sha512-1xwNTJ86L0aJmWRwENCJlH4LULMG2sOXWIVw+Szta4fkqKVY50Eo4HoVKKq6U9QEytrWCr8+zjw0q/ZOeXpcAQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@protobufjs/base64": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/base64/-/base64-1.1.2.tgz", + "integrity": "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@protobufjs/codegen": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@protobufjs/codegen/-/codegen-2.0.5.tgz", + "integrity": "sha512-zgXFLzW3Ap33e6d0Wlj4MGIm6Ce8O89n/apUaGNB/jx+hw+ruWEp7EwGUshdLKVRCxZW12fp9r40E1mQrf/34g==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@protobufjs/eventemitter": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@protobufjs/eventemitter/-/eventemitter-1.1.1.tgz", + "integrity": "sha512-vW1GmwMZNnL+gMRaovlh9yZX74kc+TTU3FObkkurpMaRtBfLP3ldjS9KQWlwZgraRE0+dheEEoAxdzcJQ8eXZg==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", - "license": "Apache-2.0", + "node_modules/@protobufjs/fetch": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@protobufjs/fetch/-/fetch-1.1.1.tgz", + "integrity": "sha512-GpptLrs57adMSuHi3VNj0mAF8dwh36LMaYF6XyJ6JMWlVsc+t42tm1HSEDmOs3A8fC9yyeisgLhsTVQokOZ0zw==", + "license": "BSD-3-Clause", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "@protobufjs/aspromise": "^1.1.1" } }, - "node_modules/@opentelemetry/exporter-trace-otlp-proto/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@protobufjs/float": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/@protobufjs/float/-/float-1.0.2.tgz", + "integrity": "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-zipkin": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/exporter-zipkin/-/exporter-zipkin-2.0.1.tgz", - "integrity": "sha512-a9eeyHIipfdxzCfc2XPrE+/TI3wmrZUDFtG2RRXHSbZZULAny7SyybSvaDvS77a7iib5MPiAvluwVvbGTsHxsw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.0.0" - } + "node_modules/@protobufjs/path": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/path/-/path-1.1.2.tgz", + "integrity": "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-zipkin/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@protobufjs/pool": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@protobufjs/pool/-/pool-1.1.0.tgz", + "integrity": "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-zipkin/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@protobufjs/utf8": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@protobufjs/utf8/-/utf8-1.1.2.tgz", + "integrity": "sha512-b1UQwcEZ4yCnMCD8DAL1VlbvBJE9/IX4FTIp7BG1xYpf29SLazLSrqUkj4w7Y5y7cCVP6E5tcqqcI0xemPkHug==", + "license": "BSD-3-Clause" }, - "node_modules/@opentelemetry/exporter-zipkin/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.62.2.tgz", + "integrity": "sha512-6o7ZLZK+BeenkZCFNDXqpbjw9bD6nuWonvS/lwQJp7NoVVxm6p3qE7qQ5jGuBjiFsgvqjD8mZAU5oWxTmbOeOg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] }, - "node_modules/@opentelemetry/instrumentation": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", - "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "import-in-the-middle": "^1.8.1", - "require-in-the-middle": "^7.1.1" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/instrumentation-express": { - "version": "0.67.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-express/-/instrumentation-express-0.67.0.tgz", - "integrity": "sha512-1WTWX2YNZIV+jPmEqdf/Vd1gHMT92TKA/0pf/iIItWhV6+RhzhnUUW4kSWQn8L3qVcgWEzQ860/ZOwaIwayi8A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "^2.0.0", - "@opentelemetry/instrumentation": "^0.219.0", - "@opentelemetry/semantic-conventions": "^1.27.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } - }, - "node_modules/@opentelemetry/instrumentation-express/node_modules/@opentelemetry/api-logs": { - "version": "0.219.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.219.0.tgz", - "integrity": "sha512-FFx7YnaYJlIjqWW/AG/yAZ0L/NEY724PipXXXQLdtZPbLwBGbUMTGL1i/esI56TWfTUXxhLfpgrnWJCG8aUJyg==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api": "^1.3.0" - }, - "engines": { - "node": ">=8.0.0" - } + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.62.2.tgz", + "integrity": "sha512-BaH7BllCACHoH1LguOU56UItGfUWjujlO65kS9LAodViaN4bwIKd7oeW/ZHJ/4ljr/7MIiENnNy3HJ0zXv8Zkw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] }, - "node_modules/@opentelemetry/instrumentation-express/node_modules/@opentelemetry/instrumentation": { - "version": "0.219.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.219.0.tgz", - "integrity": "sha512-X5t7I8GyIO9rmGHwoedZLREpQqrF1WW2nxzNNym6HOKpFiE+rvqV3ngC0xcZVO2YwIGf3KKmRdWrYwdwz3H9RQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.219.0", - "import-in-the-middle": "^3.0.0", - "require-in-the-middle": "^8.0.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.62.2.tgz", + "integrity": "sha512-v39RCCvj4He82I9sFmk+M1VZ0PLM9sfsLVikjfx2hYBNALhrrOR2D3JjQA6AhlaSOgcR+RzrKY7e1+bT6SUO/A==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] }, - "node_modules/@opentelemetry/instrumentation-express/node_modules/cjs-module-lexer": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-2.2.0.tgz", - "integrity": "sha512-4bHTS2YuzUvtoLjdy+98ykbNB5jS0+07EvFNXerqZQJ89F7DI6ET7OQo/HJuW6K0aVsKA9hj9/RVb2kQVOrPDQ==", - "license": "MIT" + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.62.2.tgz", + "integrity": "sha512-yl0y2vq3S3lHeuXhEdss6TWfKW8vkujImO12tn4ZkG/4oghr09LvdYm2RElVjokTQiUvDUGXLGsYeLqUMCKpGA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] }, - "node_modules/@opentelemetry/instrumentation-express/node_modules/import-in-the-middle": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-3.0.2.tgz", - "integrity": "sha512-LGLYRl0A2gtyUJb2WDliBHmk6TtlHwdDjxonacZ8QrEs/ZW+YDgNv2QAfjRQWpS8HqvNcq6GGnN6jrOa5FysDQ==", - "license": "Apache-2.0", - "dependencies": { - "acorn": "^8.15.0", - "acorn-import-attributes": "^1.9.5", - "cjs-module-lexer": "^2.2.0", - "module-details-from-path": "^1.0.4" - }, - "engines": { - "node": ">=18" - } + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.62.2.tgz", + "integrity": "sha512-tT4pvt4qXD+vEoezupCWi+a1F0vvDiksiHc+PxRlYTOH1I6/X4id9jPxTP+Fg+545euaFT1jJVs4CEdHZAU1vw==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] }, - "node_modules/@opentelemetry/instrumentation-express/node_modules/require-in-the-middle": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-8.0.1.tgz", - "integrity": "sha512-QT7FVMXfWOYFbeRBF6nu+I6tr2Tf3u0q8RIEjNob/heKY/nh7drD/k7eeMFmSQgnTtCzLDcCu/XEnpW2wk4xCQ==", + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.62.2.tgz", + "integrity": "sha512-6nU5F2wCW+qvCBhTn1pdIU3bzsIoF7EUwsCDRxilWGprQR6yd508YnH9+OKFCwpfS8pjZqDUmnCAr7exax0XCg==", + "cpu": [ + "x64" + ], + "dev": true, "license": "MIT", - "dependencies": { - "debug": "^4.3.5", - "module-details-from-path": "^1.0.3" - }, - "engines": { - "node": ">=9.3.0 || >=8.10.0 <9.0.0" - } + "optional": true, + "os": [ + "freebsd" + ] }, - "node_modules/@opentelemetry/instrumentation-http": { - "version": "0.219.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-http/-/instrumentation-http-0.219.0.tgz", - "integrity": "sha512-nNt1fqpyah/OKjNHdEOu8xLwISppRU2qJuF8aR+fCcftVwdFkPgtworBLA+TI1HU2iF508jcQBF2gerWczJAXg==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.8.0", - "@opentelemetry/instrumentation": "0.219.0", - "@opentelemetry/semantic-conventions": "^1.29.0", - "forwarded-parse": "2.1.2" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.62.2.tgz", + "integrity": "sha512-n1GJHPOvpIfhi3TmrCeh6S6URt9BFCt0KQE3qvexyGCTAKpR4Lg+eWvNZEqu7epxwus/8ElT3hacYEucm49SZg==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/api-logs": { - "version": "0.219.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.219.0.tgz", - "integrity": "sha512-FFx7YnaYJlIjqWW/AG/yAZ0L/NEY724PipXXXQLdtZPbLwBGbUMTGL1i/esI56TWfTUXxhLfpgrnWJCG8aUJyg==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api": "^1.3.0" - }, - "engines": { - "node": ">=8.0.0" - } + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.62.2.tgz", + "integrity": "sha512-JqgflS8wEB+UXV/vS1RpRbifGBeN4D5lz8D8oOFbFZw4vedvdOgCFAjfBmIMdW3yL10XpQQ0Ambepw6MXrhOnA==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/core": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.8.0.tgz", - "integrity": "sha512-hd1Lfh8p545nNz+jq1Ejfz+Mn1hyLuxYn1YzTfFNrxr8urEWMNQLPf1Th8kjOH+HxwawCrtgBp8JpBUR4ZSgww==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.62.2.tgz", + "integrity": "sha512-wnFJkogWvN4jm/hQRF2UBaeUmk20j5+DmHvoyWii2b8HJDyvz1MF2OU/6ynXt2KR63rbZLWkFpoytpdc/yBuSA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/@opentelemetry/instrumentation": { - "version": "0.219.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.219.0.tgz", - "integrity": "sha512-X5t7I8GyIO9rmGHwoedZLREpQqrF1WW2nxzNNym6HOKpFiE+rvqV3ngC0xcZVO2YwIGf3KKmRdWrYwdwz3H9RQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.219.0", - "import-in-the-middle": "^3.0.0", - "require-in-the-middle": "^8.0.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.62.2.tgz", + "integrity": "sha512-HVu2bp0zhvJ8xHEV9+UUs7S90VadmBSY3LcIMvozbPo4AuMGDWlz3ymHLHZPX4hR67TKTt8Qp5PJ5RBg/i+RMQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/cjs-module-lexer": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-2.2.0.tgz", - "integrity": "sha512-4bHTS2YuzUvtoLjdy+98ykbNB5jS0+07EvFNXerqZQJ89F7DI6ET7OQo/HJuW6K0aVsKA9hj9/RVb2kQVOrPDQ==", - "license": "MIT" + "node_modules/@rollup/rollup-linux-loong64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.62.2.tgz", + "integrity": "sha512-mQqqAV8QaoSgr9I2fKDLY2BAVvmKjWoGiu/cSYQonsLvtqwEn1E4QYfnCOcp5zoEqNhsDYin1s6jx/VJmrxlZg==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/import-in-the-middle": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-3.0.2.tgz", - "integrity": "sha512-LGLYRl0A2gtyUJb2WDliBHmk6TtlHwdDjxonacZ8QrEs/ZW+YDgNv2QAfjRQWpS8HqvNcq6GGnN6jrOa5FysDQ==", - "license": "Apache-2.0", - "dependencies": { - "acorn": "^8.15.0", - "acorn-import-attributes": "^1.9.5", - "cjs-module-lexer": "^2.2.0", - "module-details-from-path": "^1.0.4" - }, - "engines": { - "node": ">=18" - } + "node_modules/@rollup/rollup-linux-loong64-musl": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.62.2.tgz", + "integrity": "sha512-IxKLoxCQ2IWi6bT2akyDUBGsOImDKB+sPp4EsTmwFQ/fMwpCKm8uLSSgP/Kx/QYUgKis6SEZ5/Nlhup0DIA0PQ==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-http/node_modules/require-in-the-middle": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-8.0.1.tgz", - "integrity": "sha512-QT7FVMXfWOYFbeRBF6nu+I6tr2Tf3u0q8RIEjNob/heKY/nh7drD/k7eeMFmSQgnTtCzLDcCu/XEnpW2wk4xCQ==", + "node_modules/@rollup/rollup-linux-ppc64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.62.2.tgz", + "integrity": "sha512-Mk5ha2RQSgyFfmYYLkBpPnUk8D8FriBxesO1u9O75X0mHgXL1UQcH5Itl2lurWL2tj0RxV9b9tJgipac0hRY9A==", + "cpu": [ + "ppc64" + ], + "dev": true, "license": "MIT", - "dependencies": { - "debug": "^4.3.5", - "module-details-from-path": "^1.0.3" - }, - "engines": { - "node": ">=9.3.0 || >=8.10.0 <9.0.0" - } + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-undici": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation-undici/-/instrumentation-undici-0.6.0.tgz", - "integrity": "sha512-ABJBhm5OdhGmbh0S/fOTE4N69IZ00CsHC5ijMYfzbw3E5NwLgpQk5xsljaECrJ8wz1SfXbO03FiSuu5AyRAkvQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "^1.8.0", - "@opentelemetry/instrumentation": "^0.53.0" - }, - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.7.0" - } + "node_modules/@rollup/rollup-linux-ppc64-musl": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.62.2.tgz", + "integrity": "sha512-CjvEnqJL/0/TQ3TXX3OPIJ/kmBellrWd4heXUmHeJlTnmwjKpSJzoehLaL6Xk0ZnMHBu9dZuFADNOrtjF4v+2w==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/api-logs": { - "version": "0.53.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.53.0.tgz", - "integrity": "sha512-8HArjKx+RaAI8uEIgcORbZIPklyh1YLjPSBus8hjRmvLi6DeFzgOcdZ7KwPabKj8mXF8dX0hyfAyGfycz0DbFw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api": "^1.0.0" - }, - "engines": { - "node": ">=14" - } + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.62.2.tgz", + "integrity": "sha512-1SiZbzwdkaDURsew/tSOrooKiYy7EQGT6m8ufavAi9NEyQb/6VuIxFXAL1fqa4iZe3g4NbNk4P7J32z2tw5Mgg==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/core": { - "version": "1.30.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-1.30.1.tgz", - "integrity": "sha512-OOCM2C/QIURhJMuKaekP3TRBxBKxG/TWWA0TL2J6nXUtDnuCtccy49LUJF8xPFXMX+0LMcxFpCo8M9cGY1W6rQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "1.28.0" - }, - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@rollup/rollup-linux-riscv64-musl": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.62.2.tgz", + "integrity": "sha512-nQts12zJ3NQRoE6uYljOH89v7szzLDvG2JD/vsX+vGXU8w/At1GowTZ5/7qeFQ8m7L55rpR8Okugnuo5bgjy2Q==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/instrumentation": { - "version": "0.53.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.53.0.tgz", - "integrity": "sha512-DMwg0hy4wzf7K73JJtl95m/e0boSoWhH07rfvHvYzQtBD3Bmv0Wc1x733vyZBqmFm8OjJD0/pfiUg1W3JjFX0A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.53.0", - "@types/shimmer": "^1.2.0", - "import-in-the-middle": "^1.8.1", - "require-in-the-middle": "^7.1.1", - "semver": "^7.5.2", - "shimmer": "^1.2.1" - }, - "engines": { - "node": ">=14" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.62.2.tgz", + "integrity": "sha512-E9/ll019jhPIJgpzfZoIkBGhcz+kKNgVWYRY0zr9srBdPPFVpvOKW8VaJKUbeK+eZXyQF9ltME+Kk6affeaPgg==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/instrumentation-undici/node_modules/@opentelemetry/semantic-conventions": { - "version": "1.28.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.28.0.tgz", - "integrity": "sha512-lp4qAiMTD4sNWW4DbKLBkfiMZ4jbAboJIGOQr5DvciMRI494OapieI9qiODpOt0XBr1LjIDy1xAGAnVs5supTA==", - "license": "Apache-2.0", - "engines": { - "node": ">=14" - } + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.62.2.tgz", + "integrity": "sha512-5BqxR/pshjey51iliyzTD5Xi3EN0aLmQ2lZ3lvefVV9c82BvrLo2/6OT55iifpWBufs6kdwWbuOKS841DrmK9A==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/otlp-exporter-base": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-exporter-base/-/otlp-exporter-base-0.203.0.tgz", - "integrity": "sha512-Wbxf7k+87KyvxFr5D7uOiSq/vHXWommvdnNE7vECO3tAhsA2GfOlpWINCMWUEPdHZ7tCXxw6Epp3vgx3jU7llQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-transformer": "0.203.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.62.2.tgz", + "integrity": "sha512-uNN83XxQrRAh/w0/pmAfibcwyb6YWt4gP+dpnQKPVJshAloQ785ii8CT8ZCIxkGg9opVsvAlGhFitSm6D1Jjpg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] }, - "node_modules/@opentelemetry/otlp-exporter-base/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@rollup/rollup-openbsd-x64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.62.2.tgz", + "integrity": "sha512-srjEIxSH3LRnJN6THczDHWQplqEMFiAJrTab0msUryh9kwNpkICf3Ea6q6MN/2cZwRFUNx5w+h6Hpi4QuHS6Zg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openbsd" + ] }, - "node_modules/@opentelemetry/otlp-exporter-base/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-openharmony-arm64": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.62.2.tgz", + "integrity": "sha512-8hOJnxgbyObnCm5AlRA3A931xX19xq80RjVTKgJOvEKWqJruP/Uf12IbAOaDjjEXYRewwHLfmF0YRIdK3OwKWA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ] }, - "node_modules/@opentelemetry/otlp-exporter-base/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.62.2.tgz", + "integrity": "sha512-mmF4AY1i0hG/bLWUctUq59gtmgaSIRa3cu/A3JFRp/sCNEme2bgDEiDS22P9FbnJB8NJNF4jPJiSP5RHQpUTDg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] }, - "node_modules/@opentelemetry/otlp-exporter-base/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.62.2.tgz", + "integrity": "sha512-DZgkknc6jhHrk46V25vbAM0zZkyP0nSDkJB8/dRkLTxv470dOmWDqGoEJl/9A0dFfS7yE3REOwNDxpHwSLSt0Q==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] }, - "node_modules/@opentelemetry/otlp-grpc-exporter-base": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-grpc-exporter-base/-/otlp-grpc-exporter-base-0.203.0.tgz", - "integrity": "sha512-te0Ze1ueJF+N/UOFl5jElJW4U0pZXQ8QklgSfJ2linHN0JJsuaHG8IabEUi2iqxY8ZBDlSiz1Trfv5JcjWWWwQ==", - "license": "Apache-2.0", - "dependencies": { - "@grpc/grpc-js": "^1.7.1", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/otlp-exporter-base": "0.203.0", - "@opentelemetry/otlp-transformer": "0.203.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@rollup/rollup-win32-x64-gnu": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.62.2.tgz", + "integrity": "sha512-T6xr6ucWSFto+VGajA8YH26LdpHRuP4YLHEKAtCWvJDOlnmWcDZVCI2Jmjr+IFHDlt2zRaTAKE4tfjTaWLgJBg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] }, - "node_modules/@opentelemetry/otlp-grpc-exporter-base/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.62.2.tgz", + "integrity": "sha512-BfzEnDJOt9T8M989/lA37EcJgat01wLRnoi5dQf3QzOH7jzpqTAzdDbVfRljVr5r+jzKqpbHeyOfAaXxAd0PAA==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] }, - "node_modules/@opentelemetry/otlp-grpc-exporter-base/node_modules/@opentelemetry/otlp-transformer": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.203.0.tgz", - "integrity": "sha512-Y8I6GgoCna0qDQ2W6GCRtaF24SnvqvA8OfeTi7fqigD23u8Jpb4R5KFv/pRvrlGagcCLICMIyh9wiejp4TXu/A==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "protobufjs": "^7.3.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" - } + "node_modules/@standard-schema/spec": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@standard-schema/spec/-/spec-1.1.0.tgz", + "integrity": "sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==", + "license": "MIT" }, - "node_modules/@opentelemetry/otlp-grpc-exporter-base/node_modules/@opentelemetry/resources": { + "node_modules/@tootallnate/once": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, + "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.1.tgz", + "integrity": "sha512-HqmEUIGRJ5fSXchkVgR5F7qn48bDBzv0kWj/Kfu5e6uci4UlEeng4331LnBkWffb++Ei3FOVLxo8JJWMFBDMeQ==", + "license": "MIT", "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">= 10" } }, - "node_modules/@opentelemetry/otlp-grpc-exporter-base/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", + "node_modules/@traceloop/ai-semantic-conventions": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/ai-semantic-conventions/-/ai-semantic-conventions-0.27.0.tgz", + "integrity": "sha512-kT/0ftxCHIRDW7DZ4uip1qRBv3hvOqqTkPJUNnjPSIW1Tie7Pe5N8aeVUGEzjz32eTS7vRdO/CUws8Shr5f6yA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/semantic-conventions": "^1.40.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/otlp-transformer": { - "version": "0.211.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/otlp-transformer/-/otlp-transformer-0.211.0.tgz", - "integrity": "sha512-julhCJ9dXwkOg9svuuYqqjXLhVaUgyUvO2hWbTxwjvLXX2rG3VtAaB0SzxMnGTuoCZizBT7Xqqm2V7+ggrfCXA==", + "node_modules/@traceloop/instrumentation-anthropic": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-anthropic/-/instrumentation-anthropic-0.27.0.tgz", + "integrity": "sha512-9ya3GxvTFdgA4sJjuPz7RCQh7jQlCxaOJzXSibT6CX+L2zP/6nJBJhgjT4jiLU0D1+JKOEIfArTsEduJ/Uvzow==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.211.0", - "@opentelemetry/core": "2.5.0", - "@opentelemetry/resources": "2.5.0", - "@opentelemetry/sdk-logs": "0.211.0", - "@opentelemetry/sdk-metrics": "2.5.0", - "@opentelemetry/sdk-trace-base": "2.5.0", - "protobufjs": "8.0.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": "^1.3.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/api-logs": { - "version": "0.211.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.211.0.tgz", - "integrity": "sha512-swFdZq8MCdmdR22jTVGQDhwqDzcI4M10nhjXkLr1EsIzXgZBqm4ZlmmcWsg3TSNf+3mzgOiqveXmBLZuDi2Lgg==", + "node_modules/@traceloop/instrumentation-anthropic/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.3.0" @@ -2270,1165 +1995,1024 @@ "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/core": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.5.0.tgz", - "integrity": "sha512-ka4H8OM6+DlUhSAZpONu0cPBtPPTQKxbxVzC4CzVx5+K4JnroJVBtDzLAMx4/3CDTJXRvVFhpFjtl4SaiTNoyQ==", + "node_modules/@traceloop/instrumentation-anthropic/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/resources": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.5.0.tgz", - "integrity": "sha512-F8W52ApePshpoSrfsSk1H2yJn9aKjCrbpQF1M9Qii0GHzbfVeFUB+rc3X4aggyZD8x9Gu3Slua+s6krmq6Dt8g==", - "license": "Apache-2.0", - "dependencies": { - "@opentelemetry/core": "2.5.0", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" - } + "node_modules/@traceloop/instrumentation-anthropic/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-logs": { - "version": "0.211.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.211.0.tgz", - "integrity": "sha512-O5nPwzgg2JHzo59kpQTPUOTzFi0Nv5LxryG27QoXBciX3zWM3z83g+SNOHhiQVYRWFSxoWn1JM2TGD5iNjOwdA==", + "node_modules/@traceloop/instrumentation-anthropic/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.211.0", - "@opentelemetry/core": "2.5.0", - "@opentelemetry/resources": "2.5.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.4.0 <1.10.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-metrics": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.5.0.tgz", - "integrity": "sha512-BeJLtU+f5Gf905cJX9vXFQorAr6TAfK3SPvTFqP+scfIpDQEJfRaGJWta7sJgP+m4dNtBf9y3yvBKVAZZtJQVA==", - "license": "Apache-2.0", + "node_modules/@traceloop/instrumentation-anthropic/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", "dependencies": { - "@opentelemetry/core": "2.5.0", - "@opentelemetry/resources": "2.5.0" + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.9.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.5.0.tgz", - "integrity": "sha512-VzRf8LzotASEyNDUxTdaJ9IRJ1/h692WyArDBInf5puLCjxbICD6XkHgpuudis56EndyS7LYFmtTMny6UABNdQ==", + "node_modules/@traceloop/instrumentation-bedrock": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-bedrock/-/instrumentation-bedrock-0.27.0.tgz", + "integrity": "sha512-6u8wELcQPDa3IfujOw5W86tzerXjYXXtdh9ELTJ6oo21w06JzFaFdJ/f3xttg2q8mHtVLGgrlIJLJdmgqyaLgQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.5.0", - "@opentelemetry/resources": "2.5.0", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/otlp-transformer/node_modules/protobufjs": { - "version": "8.0.0", - "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-8.0.0.tgz", - "integrity": "sha512-jx6+sE9h/UryaCZhsJWbJtTEy47yXoGNYI4z8ZaRncM0zBKeRqjO2JEcOUYwrYGb1WLhXM1FfMzW3annvFv0rw==", - "hasInstallScript": true, - "license": "BSD-3-Clause", + "node_modules/@traceloop/instrumentation-bedrock/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", "dependencies": { - "@protobufjs/aspromise": "^1.1.2", - "@protobufjs/base64": "^1.1.2", - "@protobufjs/codegen": "^2.0.4", - "@protobufjs/eventemitter": "^1.1.0", - "@protobufjs/fetch": "^1.1.0", - "@protobufjs/float": "^1.0.2", - "@protobufjs/inquire": "^1.1.0", - "@protobufjs/path": "^1.1.2", - "@protobufjs/pool": "^1.1.0", - "@protobufjs/utf8": "^1.1.0", - "@types/node": ">=13.7.0", - "long": "^5.0.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": ">=12.0.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/propagator-b3": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-b3/-/propagator-b3-2.0.1.tgz", - "integrity": "sha512-Hc09CaQ8Tf5AGLmf449H726uRoBNGPBL4bjr7AnnUpzWMvhdn61F78z9qb6IqB737TffBsokGAK1XykFEZ1igw==", + "node_modules/@traceloop/instrumentation-bedrock/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/propagator-b3/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@traceloop/instrumentation-bedrock/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-bedrock/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@opentelemetry/propagator-jaeger": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/propagator-jaeger/-/propagator-jaeger-2.0.1.tgz", - "integrity": "sha512-7PMdPBmGVH2eQNb/AtSJizQNgeNTfh6jQFqys6lfhd6P4r+m/nTh3gKPPpaCXVdRQ+z93vfKk+4UGty390283w==", - "license": "Apache-2.0", + "node_modules/@traceloop/instrumentation-bedrock/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", "dependencies": { - "@opentelemetry/core": "2.0.1" + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/propagator-jaeger/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@traceloop/instrumentation-chromadb": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-chromadb/-/instrumentation-chromadb-0.27.0.tgz", + "integrity": "sha512-UQWPHCcFelEYnUCXt6iiVkbriIV2Ku/WYCtMK+y7fFsC/kipDKfP5PpX2cNriWyJ5togGaPaxPfexkXpx6t9jA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.38.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/resources": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.4.0.tgz", - "integrity": "sha512-RWvGLj2lMDZd7M/5tjkI/2VHMpXebLgPKvBUd9LRasEWR2xAynDwEYZuLvY9P2NGG73HF07jbbgWX2C9oavcQg==", + "node_modules/@traceloop/instrumentation-chromadb/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.4.0", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/sdk-logs": { + "node_modules/@traceloop/instrumentation-chromadb/node_modules/@opentelemetry/instrumentation": { "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-logs/-/sdk-logs-0.203.0.tgz", - "integrity": "sha512-vM2+rPq0Vi3nYA5akQD2f3QwossDnTDLvKbea6u/A2NZ3XDkPxMfo/PNrDoXhDUD/0pPo2CdH5ce/thn9K0kLw==", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1" + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.4.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/sdk-logs/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@traceloop/instrumentation-chromadb/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-chromadb/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/instrumentation-chromadb/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/sdk-logs/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@traceloop/instrumentation-cohere": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-cohere/-/instrumentation-cohere-0.27.0.tgz", + "integrity": "sha512-kDiPPZ8730mLHwBpDiXqVM5CBUEpcwMGF0EoDy9DA91qaVpdSNN0i/0QhaU8kEV2wgn92aBIcQKT8isPAlQLeQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.38.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/sdk-metrics": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-metrics/-/sdk-metrics-2.0.1.tgz", - "integrity": "sha512-wf8OaJoSnujMAHWR3g+/hGvNcsC16rf9s1So4JlMiFaFHiE4HpIA3oUh+uWZQ7CNuK8gVW/pQSkgoa5HkkOl0g==", + "node_modules/@traceloop/instrumentation-cohere/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.9.0 <1.10.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/sdk-metrics/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@traceloop/instrumentation-cohere/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/sdk-metrics/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@traceloop/instrumentation-cohere/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-cohere/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/instrumentation-cohere/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/sdk-node": { - "version": "0.203.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-node/-/sdk-node-0.203.0.tgz", - "integrity": "sha512-zRMvrZGhGVMvAbbjiNQW3eKzW/073dlrSiAKPVWmkoQzah9wfynpVPeL55f9fVIm0GaBxTLcPeukWGy0/Wj7KQ==", + "node_modules/@traceloop/instrumentation-google-generativeai": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-google-generativeai/-/instrumentation-google-generativeai-0.27.0.tgz", + "integrity": "sha512-KaUPMITuSv/mXNs37U/NpMXmkctSiq4iwQY+y025m+as1rUn4gGdjdTzYl666f5DuMLpi/0HWfyk4fh1hDmPdQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api-logs": "0.203.0", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/exporter-logs-otlp-grpc": "0.203.0", - "@opentelemetry/exporter-logs-otlp-http": "0.203.0", - "@opentelemetry/exporter-logs-otlp-proto": "0.203.0", - "@opentelemetry/exporter-metrics-otlp-grpc": "0.203.0", - "@opentelemetry/exporter-metrics-otlp-http": "0.203.0", - "@opentelemetry/exporter-metrics-otlp-proto": "0.203.0", - "@opentelemetry/exporter-prometheus": "0.203.0", - "@opentelemetry/exporter-trace-otlp-grpc": "0.203.0", - "@opentelemetry/exporter-trace-otlp-http": "0.203.0", - "@opentelemetry/exporter-trace-otlp-proto": "0.203.0", - "@opentelemetry/exporter-zipkin": "2.0.1", - "@opentelemetry/instrumentation": "0.203.0", - "@opentelemetry/propagator-b3": "2.0.1", - "@opentelemetry/propagator-jaeger": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/sdk-logs": "0.203.0", - "@opentelemetry/sdk-metrics": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1", - "@opentelemetry/sdk-trace-node": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=14" } }, - "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/context-async-hooks": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/context-async-hooks/-/context-async-hooks-2.0.1.tgz", - "integrity": "sha512-XuY23lSI3d4PEqKA+7SLtAgwqIfc6E/E9eAQWLN1vlpC53ybO3o6jW4BsXo1xvz9lYyyWItfQDDLzezER01mCw==", + "node_modules/@traceloop/instrumentation-google-generativeai/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", - "engines": { - "node": "^18.19.0 || >=20.6.0" + "dependencies": { + "@opentelemetry/api": "^1.3.0" }, - "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "engines": { + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/core": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/core/-/core-2.0.1.tgz", - "integrity": "sha512-MaZk9SJIDgo1peKevlbhP6+IwIiNPNmswNL4AF0WaQJLbHXjr9SrZMgS12+iqr9ToV4ZVosCcc0f8Rg67LXjxw==", + "node_modules/@traceloop/instrumentation-google-generativeai/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/resources": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/resources/-/resources-2.0.1.tgz", - "integrity": "sha512-dZOB3R6zvBwDKnHDTB4X1xtMArB/d324VsbiPkX/Yu0Q8T2xceRthoIVFhJdvgVM2QhGVUyX9tzwiNxGtoBJUw==", + "node_modules/@traceloop/instrumentation-google-generativeai/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-google-generativeai/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" - }, - "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.0.1.tgz", - "integrity": "sha512-xYLlvk/xdScGx1aEqvxLwf6sXQLXCjk3/1SQT9X9AoN5rXRhkdvIFShuNNmtTEPRBqcsMbS4p/gJLNI2wXaDuQ==", - "license": "Apache-2.0", + "node_modules/@traceloop/instrumentation-google-generativeai/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", "dependencies": { - "@opentelemetry/core": "2.0.1", - "@opentelemetry/resources": "2.0.1", - "@opentelemetry/semantic-conventions": "^1.29.0" + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=8.6.0" } }, - "node_modules/@opentelemetry/sdk-node/node_modules/@opentelemetry/sdk-trace-node": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-2.0.1.tgz", - "integrity": "sha512-UhdbPF19pMpBtCWYP5lHbTogLWx9N0EBxtdagvkn5YtsAnCBZzL7SjktG+ZmupRgifsHMjwUaCCaVmqGfSADmA==", + "node_modules/@traceloop/instrumentation-langchain": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-langchain/-/instrumentation-langchain-0.27.0.tgz", + "integrity": "sha512-dPkqnmXjklJhs2AMo9EezDBLAZbwSDqnNwoL1cNSYsEIgt57qkf1OkViA1XnyOFXh5GEp0Z1fLKBQV39dq5IGg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/context-async-hooks": "2.0.1", - "@opentelemetry/core": "2.0.1", - "@opentelemetry/sdk-trace-base": "2.0.1" + "@langchain/core": ">=1.0.0 <2.0.0", + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "tslib": "^2.8.1" }, "engines": { - "node": "^18.19.0 || >=20.6.0" + "node": ">=20" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" + "@langchain/core": ">=1.0.0 <2.0.0" + }, + "peerDependenciesMeta": { + "@langchain/core": { + "optional": false + } } }, - "node_modules/@opentelemetry/sdk-trace-base": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-base/-/sdk-trace-base-2.4.0.tgz", - "integrity": "sha512-WH0xXkz/OHORDLKqaxcUZS0X+t1s7gGlumr2ebiEgNZQl2b0upK2cdoD0tatf7l8iP74woGJ/Kmxe82jdvcWRw==", + "node_modules/@traceloop/instrumentation-langchain/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/core": "2.4.0", - "@opentelemetry/resources": "2.4.0", - "@opentelemetry/semantic-conventions": "^1.29.0" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": "^18.19.0 || >=20.6.0" - }, - "peerDependencies": { - "@opentelemetry/api": ">=1.3.0 <1.10.0" + "node": ">=8.0.0" } }, - "node_modules/@opentelemetry/sdk-trace-node": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/sdk-trace-node/-/sdk-trace-node-2.4.0.tgz", - "integrity": "sha512-MBc2l04hZPYygnWPT38UiOPy9ueutPqmJ47z0m9IKuoVQh3MblmbSgwspjhdHagZLfSfmlzhWR1xtbgVNmjX2A==", + "node_modules/@traceloop/instrumentation-langchain/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/context-async-hooks": "2.4.0", - "@opentelemetry/core": "2.4.0", - "@opentelemetry/sdk-trace-base": "2.4.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { "node": "^18.19.0 || >=20.6.0" }, "peerDependencies": { - "@opentelemetry/api": ">=1.0.0 <1.10.0" - } - }, - "node_modules/@opentelemetry/semantic-conventions": { - "version": "1.39.0", - "resolved": "https://registry.npmjs.org/@opentelemetry/semantic-conventions/-/semantic-conventions-1.39.0.tgz", - "integrity": "sha512-R5R9tb2AXs2IRLNKLBJDynhkfmx7mX0vi8NkhZb3gUkPWHn6HXk5J8iQ/dql0U3ApfWym4kXXmBDRGO+oeOfjg==", - "license": "Apache-2.0", - "engines": { - "node": ">=14" + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@protobufjs/aspromise": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@protobufjs/aspromise/-/aspromise-1.1.2.tgz", - "integrity": "sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/base64": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@protobufjs/base64/-/base64-1.1.2.tgz", - "integrity": "sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/codegen": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@protobufjs/codegen/-/codegen-2.0.4.tgz", - "integrity": "sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/eventemitter": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@protobufjs/eventemitter/-/eventemitter-1.1.0.tgz", - "integrity": "sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q==", - "license": "BSD-3-Clause" + "node_modules/@traceloop/instrumentation-langchain/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" }, - "node_modules/@protobufjs/fetch": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@protobufjs/fetch/-/fetch-1.1.0.tgz", - "integrity": "sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ==", - "license": "BSD-3-Clause", + "node_modules/@traceloop/instrumentation-langchain/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", "dependencies": { - "@protobufjs/aspromise": "^1.1.1", - "@protobufjs/inquire": "^1.1.0" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@protobufjs/float": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/@protobufjs/float/-/float-1.0.2.tgz", - "integrity": "sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/inquire": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@protobufjs/inquire/-/inquire-1.1.0.tgz", - "integrity": "sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/path": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/@protobufjs/path/-/path-1.1.2.tgz", - "integrity": "sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/pool": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@protobufjs/pool/-/pool-1.1.0.tgz", - "integrity": "sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw==", - "license": "BSD-3-Clause" - }, - "node_modules/@protobufjs/utf8": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/@protobufjs/utf8/-/utf8-1.1.0.tgz", - "integrity": "sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw==", - "license": "BSD-3-Clause" - }, - "node_modules/@rollup/rollup-android-arm-eabi": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.55.2.tgz", - "integrity": "sha512-21J6xzayjy3O6NdnlO6aXi/urvSRjm6nCI6+nF6ra2YofKruGixN9kfT+dt55HVNwfDmpDHJcaS3JuP/boNnlA==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ] - }, - "node_modules/@rollup/rollup-android-arm64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.55.2.tgz", - "integrity": "sha512-eXBg7ibkNUZ+sTwbFiDKou0BAckeV6kIigK7y5Ko4mB/5A1KLhuzEKovsmfvsL8mQorkoincMFGnQuIT92SKqA==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "android" - ] - }, - "node_modules/@rollup/rollup-darwin-arm64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.55.2.tgz", - "integrity": "sha512-UCbaTklREjrc5U47ypLulAgg4njaqfOVLU18VrCrI+6E5MQjuG0lSWaqLlAJwsD7NpFV249XgB0Bi37Zh5Sz4g==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ] - }, - "node_modules/@rollup/rollup-darwin-x64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.55.2.tgz", - "integrity": "sha512-dP67MA0cCMHFT2g5XyjtpVOtp7y4UyUxN3dhLdt11at5cPKnSm4lY+EhwNvDXIMzAMIo2KU+mc9wxaAQJTn7sQ==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "darwin" - ] - }, - "node_modules/@rollup/rollup-freebsd-arm64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.55.2.tgz", - "integrity": "sha512-WDUPLUwfYV9G1yxNRJdXcvISW15mpvod1Wv3ok+Ws93w1HjIVmCIFxsG2DquO+3usMNCpJQ0wqO+3GhFdl6Fow==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ] - }, - "node_modules/@rollup/rollup-freebsd-x64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.55.2.tgz", - "integrity": "sha512-Ng95wtHVEulRwn7R0tMrlUuiLVL/HXA8Lt/MYVpy88+s5ikpntzZba1qEulTuPnPIZuOPcW9wNEiqvZxZmgmqQ==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "freebsd" - ] - }, - "node_modules/@rollup/rollup-linux-arm-gnueabihf": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.55.2.tgz", - "integrity": "sha512-AEXMESUDWWGqD6LwO/HkqCZgUE1VCJ1OhbvYGsfqX2Y6w5quSXuyoy/Fg3nRqiwro+cJYFxiw5v4kB2ZDLhxrw==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@rollup/rollup-linux-arm-musleabihf": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.55.2.tgz", - "integrity": "sha512-ZV7EljjBDwBBBSv570VWj0hiNTdHt9uGznDtznBB4Caj3ch5rgD4I2K1GQrtbvJ/QiB+663lLgOdcADMNVC29Q==", - "cpu": [ - "arm" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@rollup/rollup-linux-arm64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.55.2.tgz", - "integrity": "sha512-uvjwc8NtQVPAJtq4Tt7Q49FOodjfbf6NpqXyW/rjXoV+iZ3EJAHLNAnKT5UJBc6ffQVgmXTUL2ifYiLABlGFqA==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@rollup/rollup-linux-arm64-musl": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.55.2.tgz", - "integrity": "sha512-s3KoWVNnye9mm/2WpOZ3JeUiediUVw6AvY/H7jNA6qgKA2V2aM25lMkVarTDfiicn/DLq3O0a81jncXszoyCFA==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@rollup/rollup-linux-loong64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.55.2.tgz", - "integrity": "sha512-gi21faacK+J8aVSyAUptML9VQN26JRxe484IbF+h3hpG+sNVoMXPduhREz2CcYr5my0NE3MjVvQ5bMKX71pfVA==", - "cpu": [ - "loong64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] - }, - "node_modules/@rollup/rollup-linux-loong64-musl": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.55.2.tgz", - "integrity": "sha512-qSlWiXnVaS/ceqXNfnoFZh4IiCA0EwvCivivTGbEu1qv2o+WTHpn1zNmCTAoOG5QaVr2/yhCoLScQtc/7RxshA==", - "cpu": [ - "loong64" - ], - "dev": true, + "node_modules/@traceloop/instrumentation-langchain/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } }, - "node_modules/@rollup/rollup-linux-ppc64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.55.2.tgz", - "integrity": "sha512-rPyuLFNoF1B0+wolH277E780NUKf+KoEDb3OyoLbAO18BbeKi++YN6gC/zuJoPPDlQRL3fIxHxCxVEWiem2yXw==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-llamaindex": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-llamaindex/-/instrumentation-llamaindex-0.27.0.tgz", + "integrity": "sha512-AawF5PyzmrdExFGvBE4nbng95tAu46pSSViiOeocL232/BRnmMiIG+NeGTJuUBdNrdIRbcy/FtCux+Vzc6zP8A==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "lodash": "^4.17.21", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=14" + } }, - "node_modules/@rollup/rollup-linux-ppc64-musl": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.55.2.tgz", - "integrity": "sha512-g+0ZLMook31iWV4PvqKU0i9E78gaZgYpSrYPed/4Bu+nGTgfOPtfs1h11tSSRPXSjC5EzLTjV/1A7L2Vr8pJoQ==", - "cpu": [ - "ppc64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-llamaindex/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, + "engines": { + "node": ">=8.0.0" + } }, - "node_modules/@rollup/rollup-linux-riscv64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.55.2.tgz", - "integrity": "sha512-i+sGeRGsjKZcQRh3BRfpLsM3LX3bi4AoEVqmGDyc50L6KfYsN45wVCSz70iQMwPWr3E5opSiLOwsC9WB4/1pqg==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-llamaindex/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } }, - "node_modules/@rollup/rollup-linux-riscv64-musl": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.55.2.tgz", - "integrity": "sha512-C1vLcKc4MfFV6I0aWsC7B2Y9QcsiEcvKkfxprwkPfLaN8hQf0/fKHwSF2lcYzA9g4imqnhic729VB9Fo70HO3Q==", - "cpu": [ - "riscv64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-llamaindex/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" }, - "node_modules/@rollup/rollup-linux-s390x-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.55.2.tgz", - "integrity": "sha512-68gHUK/howpQjh7g7hlD9DvTTt4sNLp1Bb+Yzw2Ki0xvscm2cOdCLZNJNhd2jW8lsTPrHAHuF751BygifW4bkQ==", - "cpu": [ - "s390x" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-llamaindex/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", + "dependencies": { + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } }, - "node_modules/@rollup/rollup-linux-x64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.55.2.tgz", - "integrity": "sha512-1e30XAuaBP1MAizaOBApsgeGZge2/Byd6wV4a8oa6jPdHELbRHBiw7wvo4dp7Ie2PE8TZT4pj9RLGZv9N4qwlw==", - "cpu": [ - "x64" - ], - "dev": true, + "node_modules/@traceloop/instrumentation-llamaindex/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } }, - "node_modules/@rollup/rollup-linux-x64-musl": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.55.2.tgz", - "integrity": "sha512-4BJucJBGbuGnH6q7kpPqGJGzZnYrpAzRd60HQSt3OpX/6/YVgSsJnNzR8Ot74io50SeVT4CtCWe/RYIAymFPwA==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "linux" - ] + "node_modules/@traceloop/instrumentation-mcp": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-mcp/-/instrumentation-mcp-0.27.0.tgz", + "integrity": "sha512-7Aen9J4JkYav3u43vZhzTZXI8pve1Nx3P+zdI67KMkhZRLIUNizlcP34Slwn+P404TEgOUax30nn23FRI9Lc8w==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.38.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=14" + } }, - "node_modules/@rollup/rollup-openbsd-x64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.55.2.tgz", - "integrity": "sha512-cT2MmXySMo58ENv8p6/O6wI/h/gLnD3D6JoajwXFZH6X9jz4hARqUhWpGuQhOgLNXscfZYRQMJvZDtWNzMAIDw==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "openbsd" - ] + "node_modules/@traceloop/instrumentation-mcp/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, + "engines": { + "node": ">=8.0.0" + } }, - "node_modules/@rollup/rollup-openharmony-arm64": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.55.2.tgz", - "integrity": "sha512-sZnyUgGkuzIXaK3jNMPmUIyJrxu/PjmATQrocpGA1WbCPX8H5tfGgRSuYtqBYAvLuIGp8SPRb1O4d1Fkb5fXaQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "openharmony" - ] + "node_modules/@traceloop/instrumentation-mcp/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } }, - "node_modules/@rollup/rollup-win32-arm64-msvc": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.55.2.tgz", - "integrity": "sha512-sDpFbenhmWjNcEbBcoTV0PWvW5rPJFvu+P7XoTY0YLGRupgLbFY0XPfwIbJOObzO7QgkRDANh65RjhPmgSaAjQ==", - "cpu": [ - "arm64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "node_modules/@traceloop/instrumentation-mcp/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" }, - "node_modules/@rollup/rollup-win32-ia32-msvc": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.55.2.tgz", - "integrity": "sha512-GvJ03TqqaweWCigtKQVBErw2bEhu1tyfNQbarwr94wCGnczA9HF8wqEe3U/Lfu6EdeNP0p6R+APeHVwEqVxpUQ==", - "cpu": [ - "ia32" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "node_modules/@traceloop/instrumentation-mcp/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", + "dependencies": { + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } }, - "node_modules/@rollup/rollup-win32-x64-gnu": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.55.2.tgz", - "integrity": "sha512-KvXsBvp13oZz9JGe5NYS7FNizLe99Ny+W8ETsuCyjXiKdiGrcz2/J/N8qxZ/RSwivqjQguug07NLHqrIHrqfYw==", - "cpu": [ - "x64" - ], - "dev": true, + "node_modules/@traceloop/instrumentation-mcp/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } }, - "node_modules/@rollup/rollup-win32-x64-msvc": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.55.2.tgz", - "integrity": "sha512-xNO+fksQhsAckRtDSPWaMeT1uIM+JrDRXlerpnWNXhn1TdB3YZ6uKBMBTKP0eX9XtYEP978hHk1f8332i2AW8Q==", - "cpu": [ - "x64" - ], - "dev": true, - "license": "MIT", - "optional": true, - "os": [ - "win32" - ] + "node_modules/@traceloop/instrumentation-openai": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-openai/-/instrumentation-openai-0.27.0.tgz", + "integrity": "sha512-tZhyYsxZvJV+Kif/3A7F1rNx5SHSinLg/1Q54+9izrH+kA9c/Bcx3W+Qe2n3sWWRUnFzd71P/2JryYq1MGCccQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.9.0", + "@opentelemetry/core": "^2.0.1", + "@opentelemetry/instrumentation": "^0.203.0", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "js-tiktoken": "^1.0.20", + "tslib": "^2.8.1" + }, + "engines": { + "node": ">=14" + } }, - "node_modules/@tootallnate/once": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz", - "integrity": "sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==", - "license": "MIT", + "node_modules/@traceloop/instrumentation-openai/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, "engines": { - "node": ">= 10" + "node": ">=8.0.0" } }, - "node_modules/@traceloop/ai-semantic-conventions": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/ai-semantic-conventions/-/ai-semantic-conventions-0.22.5.tgz", - "integrity": "sha512-4WWIHGbGr7RlEGHN+fBnRnqV211H540QOPe8SRg0rqYHLhBt3nAG5S0/dQq9Zmjq7R+lLkSDx2Q8U6A5zi4z5w==", + "node_modules/@traceloop/instrumentation-openai/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/semantic-conventions": "^1.38.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { - "node": ">=14" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@traceloop/instrumentation-anthropic": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-anthropic/-/instrumentation-anthropic-0.22.6.tgz", - "integrity": "sha512-Ht+xNztNm0v6vzQZh/oV1fRF+O0k/6wv/fekDPU6Fz8gNlVrIxfOX6ZMkLFikqH+R+apdS2Yk3Mg82d7VmWgNA==", + "node_modules/@traceloop/instrumentation-openai/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-openai/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "tslib": "^2.8.1" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/instrumentation-openai/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": ">=14" + "node": ">=8.6.0" } }, - "node_modules/@traceloop/instrumentation-bedrock": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-bedrock/-/instrumentation-bedrock-0.22.6.tgz", - "integrity": "sha512-w04CAPjibwkVrj+xgqLJPzJmDMa10xQIR6FmE7a+AtyRGhPdldxKZ6nkz6OCqUVWxPPWB704SEpwACc0tg31aw==", + "node_modules/@traceloop/instrumentation-pinecone": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-pinecone/-/instrumentation-pinecone-0.27.0.tgz", + "integrity": "sha512-YuE1C95p9bWTWJFbSg2x87Z8QQHMoLTRx1bFHFM39qELYZ45yKG0U6qPirywGR2U6BVXqknkg4K4Pt83bK766g==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/instrumentation": "^0.203.0", "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", + "@traceloop/ai-semantic-conventions": "0.27.0", "tslib": "^2.8.1" }, "engines": { "node": ">=14" } }, - "node_modules/@traceloop/instrumentation-chromadb": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-chromadb/-/instrumentation-chromadb-0.22.5.tgz", - "integrity": "sha512-I1zqjgXGzbvTvXn/N1a118KEhII4nxWrb5ZoBAZ78ZvWmpMiU0nBCL40K+cwpizhAhs56kz15X2GvmjExp/afg==", + "node_modules/@traceloop/instrumentation-pinecone/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "tslib": "^2.8.1" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": ">=14" + "node": ">=8.0.0" } }, - "node_modules/@traceloop/instrumentation-cohere": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-cohere/-/instrumentation-cohere-0.22.6.tgz", - "integrity": "sha512-CpLNEH6raUUALuDG4wT9BqZWn60DmOesFkAxUhMx2xxDjoAuy9OqtkPe54/0mIKOA2Z5JN8JTWvYHItbooI73A==", + "node_modules/@traceloop/instrumentation-pinecone/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "tslib": "^2.8.1" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { - "node": ">=14" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@traceloop/instrumentation-langchain": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-langchain/-/instrumentation-langchain-0.22.6.tgz", - "integrity": "sha512-+OkE4LP7sl5/jSDFIesM97irhdroW76Aa6nGbngT0LxUiqqwyH4+F+1+MaamCxZobaAqeBzSNKi3/qcAcPTfkg==", + "node_modules/@traceloop/instrumentation-pinecone/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-pinecone/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", + "dependencies": { + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/instrumentation-pinecone/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/@traceloop/instrumentation-qdrant": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-qdrant/-/instrumentation-qdrant-0.27.0.tgz", + "integrity": "sha512-DFI7mt5G30X3y/b7HU23MPm7nkNnW+vKui8PL5AKqcRNlJAJh53FrMel5BOnhMumC1yf1ZJX6mhkhE9gtwc5Ug==", "license": "Apache-2.0", "dependencies": { - "@langchain/core": "^0.3.80", "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", + "@traceloop/ai-semantic-conventions": "0.27.0", "tslib": "^2.8.1" }, "engines": { "node": ">=14" } }, - "node_modules/@traceloop/instrumentation-langchain/node_modules/@langchain/core": { - "version": "0.3.80", - "resolved": "https://registry.npmjs.org/@langchain/core/-/core-0.3.80.tgz", - "integrity": "sha512-vcJDV2vk1AlCwSh3aBm/urQ1ZrlXFFBocv11bz/NBUfLWD5/UDNMzwPdaAd2dKvNmTWa9FM2lirLU3+JCf4cRA==", - "license": "MIT", + "node_modules/@traceloop/instrumentation-qdrant/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", "dependencies": { - "@cfworker/json-schema": "^4.0.2", - "ansi-styles": "^5.0.0", - "camelcase": "6", - "decamelize": "1.2.0", - "js-tiktoken": "^1.0.12", - "langsmith": "^0.3.67", - "mustache": "^4.2.0", - "p-queue": "^6.6.2", - "p-retry": "4", - "uuid": "^10.0.0", - "zod": "^3.25.32", - "zod-to-json-schema": "^3.22.3" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": ">=18" + "node": ">=8.0.0" } }, - "node_modules/@traceloop/instrumentation-langchain/node_modules/langsmith": { - "version": "0.3.87", - "resolved": "https://registry.npmjs.org/langsmith/-/langsmith-0.3.87.tgz", - "integrity": "sha512-XXR1+9INH8YX96FKWc5tie0QixWz6tOqAsAKfcJyPkE0xPep+NDz0IQLR32q4bn10QK3LqD2HN6T3n6z1YLW7Q==", - "license": "MIT", + "node_modules/@traceloop/instrumentation-qdrant/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", + "license": "Apache-2.0", "dependencies": { - "@types/uuid": "^10.0.0", - "chalk": "^4.1.2", - "console-table-printer": "^2.12.1", - "p-queue": "^6.6.2", - "semver": "^7.6.3", - "uuid": "^10.0.0" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, - "peerDependencies": { - "@opentelemetry/api": "*", - "@opentelemetry/exporter-trace-otlp-proto": "*", - "@opentelemetry/sdk-trace-base": "*", - "openai": "*" + "engines": { + "node": "^18.19.0 || >=20.6.0" }, - "peerDependenciesMeta": { - "@opentelemetry/api": { - "optional": true - }, - "@opentelemetry/exporter-trace-otlp-proto": { - "optional": true - }, - "@opentelemetry/sdk-trace-base": { - "optional": true - }, - "openai": { - "optional": true - } + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@traceloop/instrumentation-langchain/node_modules/p-retry": { - "version": "4.6.2", - "resolved": "https://registry.npmjs.org/p-retry/-/p-retry-4.6.2.tgz", - "integrity": "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==", - "license": "MIT", + "node_modules/@traceloop/instrumentation-qdrant/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-qdrant/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", "dependencies": { - "@types/retry": "0.12.0", - "retry": "^0.13.1" - }, - "engines": { - "node": ">=8" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@traceloop/instrumentation-langchain/node_modules/zod": { - "version": "3.25.76", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.76.tgz", - "integrity": "sha512-gzUt/qt81nXsFGKIFcC3YnfEAx5NkunCfnDlvuBSSFS02bcXu4Lmea0AFIUwbLWxWPx3d9p8S5QoaujKcNQxcQ==", + "node_modules/@traceloop/instrumentation-qdrant/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "funding": { - "url": "https://github.com/sponsors/colinhacks" + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" } }, - "node_modules/@traceloop/instrumentation-llamaindex": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-llamaindex/-/instrumentation-llamaindex-0.22.6.tgz", - "integrity": "sha512-iCQ8MBcwEDradv41zU7VFF1n1Zx/jxXCpLjPTmNjhh3Jy3TfL34A2HstohfWF9qZM2fO4nOQM1QTF30bPd70lA==", + "node_modules/@traceloop/instrumentation-together": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-together/-/instrumentation-together-0.27.0.tgz", + "integrity": "sha512-dSKgjL3eC6D8eY6KDa2TY7j7qiIv6UJ39+Zjf8g+gCWp+AhUguFvZJUikeZ2RHUsEc3Qm2wx+7TpBHYmP3/hHg==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/instrumentation": "^0.203.0", "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "lodash": "^4.17.21", + "@traceloop/ai-semantic-conventions": "0.27.0", + "js-tiktoken": "^1.0.20", "tslib": "^2.8.1" }, "engines": { "node": ">=14" } }, - "node_modules/@traceloop/instrumentation-mcp": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-mcp/-/instrumentation-mcp-0.22.6.tgz", - "integrity": "sha512-dKvYmWOOurgP1TNBSAi9zECQk4+a2ActM2tUycPMMjUO3gws563Dj4PQ7JBWDCx7bz28Ss9AElRAzkJTJqaetg==", + "node_modules/@traceloop/instrumentation-together/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@traceloop/instrumentation-together/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@traceloop/instrumentation-together/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-together/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", + "dependencies": { + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/instrumentation-together/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/@traceloop/instrumentation-utils": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-utils/-/instrumentation-utils-0.27.0.tgz", + "integrity": "sha512-MUwSd1YRjj+XtYM0v29uCjAfLRUSTiDlNarH3x4D4lv0r3YiCudDiPaw8IT3XpBWvDKPjeLDZlgno+wfk8/UQg==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", + "@opentelemetry/semantic-conventions": "^1.40.0", "tslib": "^2.8.1" }, "engines": { "node": ">=14" } }, - "node_modules/@traceloop/instrumentation-openai": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-openai/-/instrumentation-openai-0.22.5.tgz", - "integrity": "sha512-RAB3cY6UeaVwKqBysi956H16jz4KXGBTXGMzsh1FUptiMAEPBzlvv39fMDxiuWRH9Z+/Haf3E3LEfKDqJvfyAg==", + "node_modules/@traceloop/instrumentation-vertexai": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-vertexai/-/instrumentation-vertexai-0.27.0.tgz", + "integrity": "sha512-C1SG6TvsKH9gUoIxLvK94cD2PyC2OZHldacW99eMyapMVndMfm5RGWcVxugLD+A0yoOHxoAmvLvgRp3I3W0spA==", "license": "Apache-2.0", "dependencies": { "@opentelemetry/api": "^1.9.0", "@opentelemetry/core": "^2.0.1", "@opentelemetry/instrumentation": "^0.203.0", "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "js-tiktoken": "^1.0.20", + "@traceloop/ai-semantic-conventions": "0.27.0", + "google-gax": "^4.0.0", "tslib": "^2.8.1" }, "engines": { "node": ">=14" } }, - "node_modules/@traceloop/instrumentation-pinecone": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-pinecone/-/instrumentation-pinecone-0.22.5.tgz", - "integrity": "sha512-jvCpykjgwMM70kA6hpIfqLVUO79X43ITuJWTVGCHzTqVCiQKI8GNTN6zHdrd6Fc8FFIZu8lp30PppUJ4u/Xoug==", + "node_modules/@traceloop/instrumentation-vertexai/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "tslib": "^2.8.1" + "@opentelemetry/api": "^1.3.0" }, "engines": { - "node": ">=14" + "node": ">=8.0.0" } }, - "node_modules/@traceloop/instrumentation-qdrant": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-qdrant/-/instrumentation-qdrant-0.22.6.tgz", - "integrity": "sha512-MkMoJf9SI7RY/N9OUNN0m1+8ZTZ/C8++5IviWZLaYXyDU+y8CRb8nPB9xZUmN2YdxIJVIcFQCn4dj9GyrsVDIQ==", + "node_modules/@traceloop/instrumentation-vertexai/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "tslib": "^2.8.1" + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" }, "engines": { - "node": ">=14" + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" } }, - "node_modules/@traceloop/instrumentation-together": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-together/-/instrumentation-together-0.22.5.tgz", - "integrity": "sha512-65BLwqkmLwzg63ILb9CMMtEcS3eqoyMI3vEs7xCGe5Bt2H4rhCkb8E1BnTJwQmUbYsfikXHoHLtq50xc/5Q34g==", + "node_modules/@traceloop/instrumentation-vertexai/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/instrumentation-vertexai/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", "license": "Apache-2.0", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "js-tiktoken": "^1.0.20", - "tslib": "^2.8.1" - }, - "engines": { - "node": ">=14" + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" } }, - "node_modules/@traceloop/instrumentation-vertexai": { - "version": "0.22.5", - "resolved": "https://registry.npmjs.org/@traceloop/instrumentation-vertexai/-/instrumentation-vertexai-0.22.5.tgz", - "integrity": "sha512-nBPPDxS1lMBVpzcLJ4JFG2g8gv1nPHg1HmYI4Avhg66JmCouT2nusOaL7Ah6lGv7e7rXMbZuy+f5lZtFJdugEg==", - "license": "Apache-2.0", + "node_modules/@traceloop/instrumentation-vertexai/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "license": "MIT", "dependencies": { - "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation": "^0.203.0", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "google-gax": "^4.0.0", - "tslib": "^2.8.1" + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" }, "engines": { - "node": ">=14" + "node": ">=8.6.0" } }, "node_modules/@traceloop/node-server-sdk": { - "version": "0.22.6", - "resolved": "https://registry.npmjs.org/@traceloop/node-server-sdk/-/node-server-sdk-0.22.6.tgz", - "integrity": "sha512-pSr+v8WFWcXXlAGfbH6pl5e8EuaY+pLZJqTVytgn0sFHXaS2cTTk8VivK8WJ5uJuW1pW70GE6IjI9ACLr9Fmfg==", + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/@traceloop/node-server-sdk/-/node-server-sdk-0.27.0.tgz", + "integrity": "sha512-22BSOM+AP2sXjqFAkvmN8q206uLbKw1OQq4FVpmAm4rqGl5WKZAjfO/O+6yNmpWPp1gWBN3TZmHjAO4idUrJhQ==", "license": "Apache-2.0", "dependencies": { "@google-cloud/opentelemetry-cloud-trace-exporter": "^3.0.0", @@ -3440,20 +3024,22 @@ "@opentelemetry/sdk-node": "^0.203.0", "@opentelemetry/sdk-trace-base": "^2.0.1", "@opentelemetry/sdk-trace-node": "^2.0.1", - "@opentelemetry/semantic-conventions": "^1.38.0", - "@traceloop/ai-semantic-conventions": "0.22.5", - "@traceloop/instrumentation-anthropic": "0.22.6", - "@traceloop/instrumentation-bedrock": "0.22.6", - "@traceloop/instrumentation-chromadb": "0.22.5", - "@traceloop/instrumentation-cohere": "0.22.6", - "@traceloop/instrumentation-langchain": "0.22.6", - "@traceloop/instrumentation-llamaindex": "0.22.6", - "@traceloop/instrumentation-mcp": "0.22.6", - "@traceloop/instrumentation-openai": "0.22.5", - "@traceloop/instrumentation-pinecone": "0.22.5", - "@traceloop/instrumentation-qdrant": "0.22.6", - "@traceloop/instrumentation-together": "0.22.5", - "@traceloop/instrumentation-vertexai": "0.22.5", + "@opentelemetry/semantic-conventions": "^1.40.0", + "@traceloop/ai-semantic-conventions": "0.27.0", + "@traceloop/instrumentation-anthropic": "0.27.0", + "@traceloop/instrumentation-bedrock": "0.27.0", + "@traceloop/instrumentation-chromadb": "0.27.0", + "@traceloop/instrumentation-cohere": "0.27.0", + "@traceloop/instrumentation-google-generativeai": "0.27.0", + "@traceloop/instrumentation-langchain": "0.27.0", + "@traceloop/instrumentation-llamaindex": "0.27.0", + "@traceloop/instrumentation-mcp": "0.27.0", + "@traceloop/instrumentation-openai": "0.27.0", + "@traceloop/instrumentation-pinecone": "0.27.0", + "@traceloop/instrumentation-qdrant": "0.27.0", + "@traceloop/instrumentation-together": "0.27.0", + "@traceloop/instrumentation-utils": "0.27.0", + "@traceloop/instrumentation-vertexai": "0.27.0", "@types/nunjucks": "^3.2.6", "cross-fetch": "^4.1.0", "eventsource": "^3.0.2", @@ -3489,17 +3075,65 @@ } } }, - "node_modules/@traceloop/node-server-sdk/node_modules/uuid": { - "version": "11.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.0.tgz", - "integrity": "sha512-0/A9rDy9P7cJ+8w1c9WD9V//9Wj15Ce2MPz8Ri6032usz+NfePxx5AcN3bN+r6ZL6jEo066/yNYB3tn4pQEx+A==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], + "node_modules/@traceloop/node-server-sdk/node_modules/@opentelemetry/api-logs": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/api-logs/-/api-logs-0.203.0.tgz", + "integrity": "sha512-9B9RU0H7Ya1Dx/Rkyc4stuBZSGVQF27WigitInx2QQoj6KUpEFYPKoWjdFTunJYxmXmh17HeBvbMa1EhGyPmqQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api": "^1.3.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/@traceloop/node-server-sdk/node_modules/@opentelemetry/instrumentation": { + "version": "0.203.0", + "resolved": "https://registry.npmjs.org/@opentelemetry/instrumentation/-/instrumentation-0.203.0.tgz", + "integrity": "sha512-ke1qyM+3AK2zPuBPb6Hk/GCsc5ewbLvPNkEuELx/JmANeEp6ZjnZ+wypPAJSucTw0wvCGrUaibDSdcrGFoWxKQ==", + "license": "Apache-2.0", + "dependencies": { + "@opentelemetry/api-logs": "0.203.0", + "import-in-the-middle": "^1.8.1", + "require-in-the-middle": "^7.1.1" + }, + "engines": { + "node": "^18.19.0 || >=20.6.0" + }, + "peerDependencies": { + "@opentelemetry/api": "^1.3.0" + } + }, + "node_modules/@traceloop/node-server-sdk/node_modules/cjs-module-lexer": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", + "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "license": "MIT" + }, + "node_modules/@traceloop/node-server-sdk/node_modules/import-in-the-middle": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", + "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "license": "Apache-2.0", + "dependencies": { + "acorn": "^8.14.0", + "acorn-import-attributes": "^1.9.5", + "cjs-module-lexer": "^1.2.2", + "module-details-from-path": "^1.0.3" + } + }, + "node_modules/@traceloop/node-server-sdk/node_modules/require-in-the-middle": { + "version": "7.5.2", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", + "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", "license": "MIT", - "bin": { - "uuid": "dist/esm/bin/uuid" + "dependencies": { + "debug": "^4.3.5", + "module-details-from-path": "^1.0.3", + "resolve": "^1.22.8" + }, + "engines": { + "node": ">=8.6.0" } }, "node_modules/@tsconfig/node10": { @@ -3537,12 +3171,19 @@ "license": "MIT" }, "node_modules/@types/estree": { - "version": "1.0.8", - "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", - "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.9.tgz", + "integrity": "sha512-GhdPgy1el4/ImP05X05Uw4cw2/M93BCUmnEvWZNStlCzEKME4Fkk+YpoA5OiHNQmoS7Cafb8Xa3Pya8m1Qrzeg==", "dev": true, "license": "MIT" }, + "node_modules/@types/json-schema": { + "version": "7.0.15", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "license": "MIT", + "peer": true + }, "node_modules/@types/long": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/@types/long/-/long-4.0.2.tgz", @@ -3550,12 +3191,12 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "25.0.9", - "resolved": "https://registry.npmjs.org/@types/node/-/node-25.0.9.tgz", - "integrity": "sha512-/rpCXHlCWeqClNBwUhDcusJxXYDjZTyE8v5oTO7WbL8eij2nKhUeU89/6xgjU7N4/Vh3He0BtyhJdQbDyhiXAw==", + "version": "25.9.5", + "resolved": "https://registry.npmjs.org/@types/node/-/node-25.9.5.tgz", + "integrity": "sha512-OScDchr2fwuUmWdf4kZ9h7PcJiYDVInhJizG/biAq3cAvqwYktuy/TYGGdZNMtNTFUP7rnb0NU4TUdm82kt4Rg==", "license": "MIT", "dependencies": { - "undici-types": "~7.16.0" + "undici-types": ">=7.24.0 <7.24.7" } }, "node_modules/@types/nunjucks": { @@ -3576,11 +3217,43 @@ "form-data": "^2.5.5" } }, - "node_modules/@types/retry": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz", - "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", - "license": "MIT" + "node_modules/@types/request/node_modules/form-data": { + "version": "2.5.6", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.5.6.tgz", + "integrity": "sha512-Ogz/E85h9tlfJzpI6TuFpGcHZFhLrb9Gw8wq9v40CxSCPnv7ahKr6Xgtkn0KYCDQJ8DNn5VoMO8EXr9V5PadyA==", + "license": "MIT", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "es-set-tostringtag": "^2.1.0", + "hasown": "^2.0.4", + "mime-types": "^2.1.35", + "safe-buffer": "^5.2.1" + }, + "engines": { + "node": ">= 0.12" + } + }, + "node_modules/@types/request/node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/@types/request/node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "license": "MIT", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } }, "node_modules/@types/shimmer": { "version": "1.2.0", @@ -3594,12 +3267,6 @@ "integrity": "sha512-/Ad8+nIOV7Rl++6f1BdKxFSMgmoqEoYbHRpPcx3JEfv8VRsQe9Z4mCXeJBzxs7mbHY/XOZZuXlRNfhpVPbs6ZA==", "license": "MIT" }, - "node_modules/@types/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-7gqG38EyHgyP1S+7+xomFtL+ZNHcKv6DwNaCZmJmo1vgMugyF3TCnXVg4t1uk89mLNwnLtnY3TpOpCOyp1/xHQ==", - "license": "MIT" - }, "node_modules/a-sync-waterfall": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/a-sync-waterfall/-/a-sync-waterfall-1.0.1.tgz", @@ -3619,9 +3286,9 @@ } }, "node_modules/acorn": { - "version": "8.15.0", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", - "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", + "version": "8.17.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.17.0.tgz", + "integrity": "sha512-xRQbDb9BnwDafYNn6Vwl839DYVjqXYb1XVGtWAZ1kcDc6iwAL4hg3B1dZlRiuENFeO2H53gFG3in621AdERVAg==", "license": "MIT", "bin": { "acorn": "bin/acorn" @@ -3640,9 +3307,9 @@ } }, "node_modules/acorn-walk": { - "version": "8.3.4", - "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.4.tgz", - "integrity": "sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==", + "version": "8.3.5", + "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.3.5.tgz", + "integrity": "sha512-HEHNfbars9v4pgpW6SO1KSPkfoS0xVOM/9UzkJltjlsHZmJasxg8aXkuZa7SMf8vKGIBhpUsPluQSqhJFCqebw==", "dev": true, "license": "MIT", "dependencies": { @@ -3653,12 +3320,15 @@ } }, "node_modules/agent-base": { - "version": "7.1.4", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.4.tgz", - "integrity": "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ==", + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", + "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", "license": "MIT", + "dependencies": { + "debug": "4" + }, "engines": { - "node": ">= 14" + "node": ">= 6.0.0" } }, "node_modules/ansi-regex": { @@ -3671,12 +3341,15 @@ } }, "node_modules/ansi-styles": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", - "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", "license": "MIT", + "dependencies": { + "color-convert": "^2.0.1" + }, "engines": { - "node": ">=10" + "node": ">=8" }, "funding": { "url": "https://github.com/chalk/ansi-styles?sponsor=1" @@ -3709,51 +3382,15 @@ "license": "MIT" }, "node_modules/axios": { - "version": "1.13.4", - "resolved": "https://registry.npmjs.org/axios/-/axios-1.13.4.tgz", - "integrity": "sha512-1wVkUaAO6WyaYtCkcYCOx12ZgpGf9Zif+qXa4n+oYzK558YryKqiL6UWwd5DqiH3VRW0GYhTZQ/vlgJrCoNQlg==", + "version": "1.18.1", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.18.1.tgz", + "integrity": "sha512-3nTvFlvpn9Zu/RkHUqtc7/+al4UpRW5az71ap5zccp6e8RAYEzhMTecX8Dz1wWDYrPpUoB1HAQEGEAEvUr7S9g==", "license": "MIT", "dependencies": { - "follow-redirects": "^1.15.6", - "form-data": "^4.0.4", - "proxy-from-env": "^1.1.0" - } - }, - "node_modules/axios/node_modules/form-data": { - "version": "4.0.5", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz", - "integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==", - "license": "MIT", - "dependencies": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.8", - "es-set-tostringtag": "^2.1.0", - "hasown": "^2.0.2", - "mime-types": "^2.1.12" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/axios/node_modules/mime-db": { - "version": "1.52.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", - "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/axios/node_modules/mime-types": { - "version": "2.1.35", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", - "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "license": "MIT", - "dependencies": { - "mime-db": "1.52.0" - }, - "engines": { - "node": ">= 0.6" + "follow-redirects": "^1.16.0", + "form-data": "^4.0.5", + "https-proxy-agent": "^5.0.1", + "proxy-from-env": "^2.1.0" } }, "node_modules/base64-js": { @@ -3813,82 +3450,43 @@ "integrity": "sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==", "dev": true, "license": "MIT", - "engines": { - "node": ">=8" - } - }, - "node_modules/call-bind-apply-helpers": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", - "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", - "license": "MIT", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/camelcase": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", - "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", - "license": "MIT", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" - } - }, - "node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "license": "MIT", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" + "engines": { + "node": ">=8" } }, - "node_modules/chalk/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "node_modules/call-bind-apply-helpers": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", + "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", "license": "MIT", "dependencies": { - "color-convert": "^2.0.1" + "es-errors": "^1.3.0", + "function-bind": "^1.1.2" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": ">= 0.4" } }, - "node_modules/chalk/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "node_modules/chokidar": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", + "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", + "devOptional": true, "license": "MIT", "dependencies": { - "has-flag": "^4.0.0" + "readdirp": "^4.0.1" }, "engines": { - "node": ">=8" + "node": ">= 14.16.0" + }, + "funding": { + "url": "https://paulmillr.com/funding/" } }, "node_modules/cjs-module-lexer": { - "version": "1.4.3", - "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.4.3.tgz", - "integrity": "sha512-9z8TZaGM1pfswYeXrUpzPrkx8UnWYdhJclsiYMm6x/w5+nN+8Tf/LnAgfLGQCm59qAOxU8WwHEq2vNwF6i4j+Q==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-2.2.0.tgz", + "integrity": "sha512-4bHTS2YuzUvtoLjdy+98ykbNB5jS0+07EvFNXerqZQJ89F7DI6ET7OQo/HJuW6K0aVsKA9hj9/RVb2kQVOrPDQ==", "license": "MIT" }, "node_modules/cliui": { @@ -3961,15 +3559,6 @@ "node": "^14.18.0 || >=16.10.0" } }, - "node_modules/console-table-printer": { - "version": "2.15.0", - "resolved": "https://registry.npmjs.org/console-table-printer/-/console-table-printer-2.15.0.tgz", - "integrity": "sha512-SrhBq4hYVjLCkBVOWaTzceJalvn5K1Zq5aQA6wXC/cYjI3frKWNPEMK3sZsJfNNQApvCQmgBcc13ZKmFj8qExw==", - "license": "MIT", - "dependencies": { - "simple-wcswidth": "^1.1.2" - } - }, "node_modules/create-require": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", @@ -4003,15 +3592,6 @@ } } }, - "node_modules/decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==", - "license": "MIT", - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", @@ -4032,9 +3612,9 @@ } }, "node_modules/dotenv": { - "version": "17.2.3", - "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-17.2.3.tgz", - "integrity": "sha512-JVUnt+DUIzu87TABbhPmNfVdBDt18BLOWjMUFJMSi/Qqg7NTYtabbvSNJGOJ7afbRuv9D/lngizHtP7QyLQ+9w==", + "version": "17.4.2", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-17.4.2.tgz", + "integrity": "sha512-nI4U3TottKAcAD9LLud4Cb7b2QztQMUEfHbvhTH09bqXTxnSie8WnjPALV/WMCrJZ6UV/qHJ6L03OqO3LcdYZw==", "license": "BSD-2-Clause", "engines": { "node": ">=12" @@ -4111,10 +3691,16 @@ "node": ">= 0.4" } }, + "node_modules/es-module-lexer": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-2.3.0.tgz", + "integrity": "sha512-KLdwQm2NvGLDkQDCGvmiQrhkd0JbMzXthwQAUgWjQuQdBLFa3eiBP5arXZyA+f8x+x7OXgud6bq2rxjGtHV2tw==", + "license": "MIT" + }, "node_modules/es-object-atoms": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", - "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.2.tgz", + "integrity": "sha512-HWcBoN6NileqtSydK2FqHbS/LoDd2pqrnQHLyJzBj4kOp/ky2MWMN694xOfkK8/SnUsW2DH7EfyVlydKCsm1Zw==", "license": "MIT", "dependencies": { "es-errors": "^1.3.0" @@ -4139,9 +3725,9 @@ } }, "node_modules/esbuild": { - "version": "0.27.2", - "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.27.2.tgz", - "integrity": "sha512-HyNQImnsOC7X9PMNaCIeAm4ISCQXs5a5YasTXVliKv4uuBo1dKrG0A+uQS8M5eXjVMnLg3WgXaKvprHlFJQffw==", + "version": "0.28.1", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.28.1.tgz", + "integrity": "sha512-HrJrvZv5ayxBzPfwphOoNzkzOIIlifzk0KJrGK2c8R4+LKpMtpYLQeUdjnwjWv/LZlkH2laZk+4w78pi99D4Vw==", "dev": true, "hasInstallScript": true, "license": "MIT", @@ -4152,32 +3738,32 @@ "node": ">=18" }, "optionalDependencies": { - "@esbuild/aix-ppc64": "0.27.2", - "@esbuild/android-arm": "0.27.2", - "@esbuild/android-arm64": "0.27.2", - "@esbuild/android-x64": "0.27.2", - "@esbuild/darwin-arm64": "0.27.2", - "@esbuild/darwin-x64": "0.27.2", - "@esbuild/freebsd-arm64": "0.27.2", - "@esbuild/freebsd-x64": "0.27.2", - "@esbuild/linux-arm": "0.27.2", - "@esbuild/linux-arm64": "0.27.2", - "@esbuild/linux-ia32": "0.27.2", - "@esbuild/linux-loong64": "0.27.2", - "@esbuild/linux-mips64el": "0.27.2", - "@esbuild/linux-ppc64": "0.27.2", - "@esbuild/linux-riscv64": "0.27.2", - "@esbuild/linux-s390x": "0.27.2", - "@esbuild/linux-x64": "0.27.2", - "@esbuild/netbsd-arm64": "0.27.2", - "@esbuild/netbsd-x64": "0.27.2", - "@esbuild/openbsd-arm64": "0.27.2", - "@esbuild/openbsd-x64": "0.27.2", - "@esbuild/openharmony-arm64": "0.27.2", - "@esbuild/sunos-x64": "0.27.2", - "@esbuild/win32-arm64": "0.27.2", - "@esbuild/win32-ia32": "0.27.2", - "@esbuild/win32-x64": "0.27.2" + "@esbuild/aix-ppc64": "0.28.1", + "@esbuild/android-arm": "0.28.1", + "@esbuild/android-arm64": "0.28.1", + "@esbuild/android-x64": "0.28.1", + "@esbuild/darwin-arm64": "0.28.1", + "@esbuild/darwin-x64": "0.28.1", + "@esbuild/freebsd-arm64": "0.28.1", + "@esbuild/freebsd-x64": "0.28.1", + "@esbuild/linux-arm": "0.28.1", + "@esbuild/linux-arm64": "0.28.1", + "@esbuild/linux-ia32": "0.28.1", + "@esbuild/linux-loong64": "0.28.1", + "@esbuild/linux-mips64el": "0.28.1", + "@esbuild/linux-ppc64": "0.28.1", + "@esbuild/linux-riscv64": "0.28.1", + "@esbuild/linux-s390x": "0.28.1", + "@esbuild/linux-x64": "0.28.1", + "@esbuild/netbsd-arm64": "0.28.1", + "@esbuild/netbsd-x64": "0.28.1", + "@esbuild/openbsd-arm64": "0.28.1", + "@esbuild/openbsd-x64": "0.28.1", + "@esbuild/openharmony-arm64": "0.28.1", + "@esbuild/sunos-x64": "0.28.1", + "@esbuild/win32-arm64": "0.28.1", + "@esbuild/win32-ia32": "0.28.1", + "@esbuild/win32-x64": "0.28.1" } }, "node_modules/escalade": { @@ -4217,9 +3803,9 @@ } }, "node_modules/eventsource-parser": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.6.tgz", - "integrity": "sha512-Vo1ab+QXPzZ4tCa8SwIHJFaSzy4R6SHf7BY79rFBDf0idraZWAkYrDjDj8uWaSm3S2TK+hJ7/t1CEmZ7jXw+pg==", + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.1.0.tgz", + "integrity": "sha512-kJezFj9YFAMLeORyi7aCLxLbD5/qWMQnoMVlVPyHIll7lgRJCc3JVln9Vgl9nwQi0YkMnhdGTMNn7CkRRAptMg==", "license": "MIT", "engines": { "node": ">=18.0.0" @@ -4268,9 +3854,9 @@ } }, "node_modules/follow-redirects": { - "version": "1.15.11", - "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.11.tgz", - "integrity": "sha512-deG2P0JfjrTxl50XGCDyfI97ZGVCxIpfKYmfyrQ54n5FO/0gfIES8C/Psl6kWVDolizcaaxZJnTS0QSMxvnsBQ==", + "version": "1.16.0", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.16.0.tgz", + "integrity": "sha512-y5rN/uOsadFT/JfYwhxRS5R7Qce+g3zG97+JrtFZlC9klX/W5hD7iiLzScI4nZqUS7DNUdhPgw4xI8W2LuXlUw==", "funding": [ { "type": "individual", @@ -4288,20 +3874,19 @@ } }, "node_modules/form-data": { - "version": "2.5.5", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.5.5.tgz", - "integrity": "sha512-jqdObeR2rxZZbPSGL+3VckHMYtu+f9//KXBsVny6JSX/pa38Fy+bGjuG8eW/H6USNQWhLi8Num++cU2yOCNz4A==", + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.6.tgz", + "integrity": "sha512-vKatAh4SlVfgbv+YtmhiRjhEMJsYpsG1Y2rMQtR+SVSbytsSD1YGzDIcrAJmdFec88u/+VoGmxnl+80gL1tRCQ==", "license": "MIT", "dependencies": { "asynckit": "^0.4.0", "combined-stream": "^1.0.8", "es-set-tostringtag": "^2.1.0", - "hasown": "^2.0.2", - "mime-types": "^2.1.35", - "safe-buffer": "^5.2.1" + "hasown": "^2.0.4", + "mime-types": "^2.1.35" }, "engines": { - "node": ">= 0.12" + "node": ">= 6" } }, "node_modules/form-data/node_modules/mime-db": { @@ -4371,17 +3956,26 @@ "node": ">=14" } }, - "node_modules/gaxios/node_modules/uuid": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", - "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], + "node_modules/gaxios/node_modules/agent-base": { + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.4.tgz", + "integrity": "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ==", "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" + "engines": { + "node": ">= 14" + } + }, + "node_modules/gaxios/node_modules/https-proxy-agent": { + "version": "7.0.6", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", + "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", + "license": "MIT", + "dependencies": { + "agent-base": "^7.1.2", + "debug": "4" + }, + "engines": { + "node": ">= 14" } }, "node_modules/gcp-metadata": { @@ -4502,19 +4096,6 @@ "node": ">=6" } }, - "node_modules/google-gax/node_modules/uuid": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", - "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, "node_modules/google-logging-utils": { "version": "0.0.2", "resolved": "https://registry.npmjs.org/google-logging-utils/-/google-logging-utils-0.0.2.tgz", @@ -4549,15 +4130,6 @@ "node": ">=14.0.0" } }, - "node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "license": "MIT", - "engines": { - "node": ">=8" - } - }, "node_modules/has-symbols": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", @@ -4586,9 +4158,9 @@ } }, "node_modules/hasown": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.4.tgz", + "integrity": "sha512-T2UbfbBEF32wiepXIsMlTW9+dDYC6wMh/t/vYA4tuOMKqWz/n3vr1NFSxQiyP+zk2mXsoMA/i/7qV6LKut1t1A==", "license": "MIT", "dependencies": { "function-bind": "^1.1.2" @@ -4611,41 +4183,31 @@ "node": ">= 6" } }, - "node_modules/http-proxy-agent/node_modules/agent-base": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", - "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", - "license": "MIT", - "dependencies": { - "debug": "4" - }, - "engines": { - "node": ">= 6.0.0" - } - }, "node_modules/https-proxy-agent": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", - "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz", + "integrity": "sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==", "license": "MIT", "dependencies": { - "agent-base": "^7.1.2", + "agent-base": "6", "debug": "4" }, "engines": { - "node": ">= 14" + "node": ">= 6" } }, "node_modules/import-in-the-middle": { - "version": "1.15.0", - "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-1.15.0.tgz", - "integrity": "sha512-bpQy+CrsRmYmoPMAE/0G33iwRqwW4ouqdRg8jgbH3aKuCtOc8lxgmYXg2dMM92CRiGP660EtBcymH/eVUpCSaA==", + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/import-in-the-middle/-/import-in-the-middle-3.3.1.tgz", + "integrity": "sha512-0rymlHSFLwZ0ixx8DaQkoIyZojJPY2a0K2nEYslhKJ6jIYO/m0IcCb7iQsFPmS7WmKwISZiIrv5Icstrw/CmqA==", "license": "Apache-2.0", "dependencies": { - "acorn": "^8.14.0", - "acorn-import-attributes": "^1.9.5", - "cjs-module-lexer": "^1.2.2", - "module-details-from-path": "^1.0.3" + "cjs-module-lexer": "^2.2.0", + "es-module-lexer": "^2.2.0", + "module-details-from-path": "^1.0.4" + }, + "engines": { + "node": ">=18" } }, "node_modules/inherits": { @@ -4655,12 +4217,12 @@ "license": "ISC" }, "node_modules/is-core-module": { - "version": "2.16.1", - "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.1.tgz", - "integrity": "sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==", + "version": "2.16.2", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.16.2.tgz", + "integrity": "sha512-evOr8xfXKxE6qSR0hSXL2r3sd7ALj8+7jQEUvPYcm5sgZFdJ+AYzT6yNmJenvIYQBgIGwfwz08sL8zoL7yq2BA==", "license": "MIT", "dependencies": { - "hasown": "^2.0.2" + "hasown": "^2.0.3" }, "engines": { "node": ">= 0.4" @@ -4679,9 +4241,9 @@ } }, "node_modules/is-network-error": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/is-network-error/-/is-network-error-1.3.0.tgz", - "integrity": "sha512-6oIwpsgRfnDiyEDLMay/GqCl3HoAtH5+RUKW29gYkL0QA+ipzpDLA16yQs7/RHCSu+BwgbJaOUqa4A99qNVQVw==", + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/is-network-error/-/is-network-error-1.3.2.tgz", + "integrity": "sha512-PhBY86zaxNZUuWP6h13Vu5oFe0XY6/UlKzQnYFELzGVHygP3MxmvTfYSG7GN3aIab/iWudSMgjSnG9Dq+nHrgA==", "license": "MIT", "peer": true, "engines": { @@ -4753,24 +4315,19 @@ } }, "node_modules/langsmith": { - "version": "0.4.7", - "resolved": "https://registry.npmjs.org/langsmith/-/langsmith-0.4.7.tgz", - "integrity": "sha512-Esv5g/J8wwRwbGQr10PB9+bLsNk0mWbrXc7nnEreQDhh0azbU57I7epSnT7GC4sS4EOWavhbxk+6p8PTXtreHw==", + "version": "0.7.17", + "resolved": "https://registry.npmjs.org/langsmith/-/langsmith-0.7.17.tgz", + "integrity": "sha512-FfmxKOVp+qBkdbOWTwXxU7qeX2H40RMsLW9Us+53/4rZYl/QzfUeeBe/rE98mfuSSnEz1tOOMjoPJIYoMt1wnw==", "license": "MIT", - "peer": true, "dependencies": { - "@types/uuid": "^10.0.0", - "chalk": "^4.1.2", - "console-table-printer": "^2.12.1", - "p-queue": "^6.6.2", - "semver": "^7.6.3", - "uuid": "^10.0.0" + "p-queue": "6.6.2" }, "peerDependencies": { "@opentelemetry/api": "*", "@opentelemetry/exporter-trace-otlp-proto": "*", "@opentelemetry/sdk-trace-base": "*", - "openai": "*" + "openai": "*", + "ws": ">=7" }, "peerDependenciesMeta": { "@opentelemetry/api": { @@ -4784,6 +4341,9 @@ }, "openai": { "optional": true + }, + "ws": { + "optional": true } } }, @@ -4818,9 +4378,9 @@ } }, "node_modules/lodash": { - "version": "4.17.23", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.23.tgz", - "integrity": "sha512-LgVTMpQtIopCi79SJeDiP0TfWi5CNEc/L/aRdTh3yIvmZXTnheWpKjSZhnvMl8iXbC1tFg9gdHHDMLoV7CnG+w==", + "version": "4.18.1", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.18.1.tgz", + "integrity": "sha512-dMInicTPVE8d1e5otfwmmjlxkZoUpiVLwyeTdUsi/Caj/gfzzblBcCE5sRHV/AsjuCmxWrte2TNGSYuCeCq+0Q==", "license": "MIT" }, "node_modules/lodash.camelcase": { @@ -4887,16 +4447,16 @@ } }, "node_modules/mlly": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/mlly/-/mlly-1.8.0.tgz", - "integrity": "sha512-l8D9ODSRWLe2KHJSifWGwBqpTZXIXTeo8mlKjY+E2HAakaTeNpqAyBZ8GSqLzHgw4XmHmC8whvpjJNMbFZN7/g==", + "version": "1.8.2", + "resolved": "https://registry.npmjs.org/mlly/-/mlly-1.8.2.tgz", + "integrity": "sha512-d+ObxMQFmbt10sretNDytwt85VrbkhhUA/JBGm1MPaWJ65Cl4wOgLaB1NYvJSZ0Ef03MMEU/0xpPMXUIQ29UfA==", "dev": true, "license": "MIT", "dependencies": { - "acorn": "^8.15.0", + "acorn": "^8.16.0", "pathe": "^2.0.3", "pkg-types": "^1.3.1", - "ufo": "^1.6.1" + "ufo": "^1.6.3" } }, "node_modules/module-details-from-path": { @@ -5025,9 +4585,9 @@ } }, "node_modules/p-limit": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-7.2.0.tgz", - "integrity": "sha512-ATHLtwoTNDloHRFFxFJdHnG6n2WUeFjaR8XQMFdKIv0xkXjrER8/iG9iu265jOM95zXHAfv9oTkqhrfbIzosrQ==", + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-7.3.0.tgz", + "integrity": "sha512-7cIXg/Z0M5WZRblrsOla88S4wAK+zOQQWeBYfV3qJuJXMr+LnbYjaadrFaS0JILfEDPVqHyKnZ1Z/1d6J9VVUw==", "license": "MIT", "dependencies": { "yocto-queue": "^1.2.1" @@ -5084,9 +4644,9 @@ } }, "node_modules/papaparse": { - "version": "5.5.3", - "resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.5.3.tgz", - "integrity": "sha512-5QvjGxYVjxO59MGU2lHVYpRWBBtKHnlIAcSe1uNFCkkptUh63NFRj0FJQm7nR67puEruUci/ZkjmEFrjCAyP4A==", + "version": "5.5.4", + "resolved": "https://registry.npmjs.org/papaparse/-/papaparse-5.5.4.tgz", + "integrity": "sha512-SwzWD9gl/ElwYLCI0nUja1mFJzjq2D8ziShfNBa7zCHzkOozeOGDwHWQ+tvCzEZcewecWZ5U7kUopDnG+DFYEQ==", "license": "MIT" }, "node_modules/path-parse": { @@ -5110,9 +4670,9 @@ "license": "ISC" }, "node_modules/picomatch": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.3.tgz", - "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.5.tgz", + "integrity": "sha512-RvwwcruNjI1ncT5xRakeyS9Lf8lcItv34KD+aif+VH9kduAyfYBipGh12274xtenIPZ119/R9BdTBa8gAwSh0A==", "dev": true, "license": "MIT", "engines": { @@ -5200,34 +4760,36 @@ } }, "node_modules/protobufjs": { - "version": "7.5.4", - "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-7.5.4.tgz", - "integrity": "sha512-CvexbZtbov6jW2eXAvLukXjXUW1TzFaivC46BpWc/3BpcCysb5Vffu+B3XHMm8lVEuy2Mm4XGex8hBSg1yapPg==", + "version": "7.6.5", + "resolved": "https://registry.npmjs.org/protobufjs/-/protobufjs-7.6.5.tgz", + "integrity": "sha512-/FPD0nUc9jH6rfFjji9IBqOz4pcSE3CsT1m7Ep6Mdb0LxSUMj8hgl6GomOvZzpNpAqqGaXA0P3VSrZLFzIhQrw==", "hasInstallScript": true, "license": "BSD-3-Clause", "dependencies": { "@protobufjs/aspromise": "^1.1.2", "@protobufjs/base64": "^1.1.2", - "@protobufjs/codegen": "^2.0.4", - "@protobufjs/eventemitter": "^1.1.0", - "@protobufjs/fetch": "^1.1.0", + "@protobufjs/codegen": "^2.0.5", + "@protobufjs/eventemitter": "^1.1.1", + "@protobufjs/fetch": "^1.1.1", "@protobufjs/float": "^1.0.2", - "@protobufjs/inquire": "^1.1.0", "@protobufjs/path": "^1.1.2", "@protobufjs/pool": "^1.1.0", - "@protobufjs/utf8": "^1.1.0", + "@protobufjs/utf8": "^1.1.1", "@types/node": ">=13.7.0", - "long": "^5.0.0" + "long": "^5.3.2" }, "engines": { "node": ">=12.0.0" } }, "node_modules/proxy-from-env": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", - "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==", - "license": "MIT" + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-2.1.0.tgz", + "integrity": "sha512-cJ+oHTW1VAEa8cJslgmUZrc+sjRKgAKl3Zyse6+PV38hZe/V6Z14TbCuXcan9F9ghlz4QrFr2c92TNF82UkYHA==", + "license": "MIT", + "engines": { + "node": ">=10" + } }, "node_modules/readable-stream": { "version": "3.6.2", @@ -5243,6 +4805,20 @@ "node": ">= 6" } }, + "node_modules/readdirp": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz", + "integrity": "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==", + "devOptional": true, + "license": "MIT", + "engines": { + "node": ">= 14.18.0" + }, + "funding": { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + }, "node_modules/require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", @@ -5253,25 +4829,25 @@ } }, "node_modules/require-in-the-middle": { - "version": "7.5.2", - "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-7.5.2.tgz", - "integrity": "sha512-gAZ+kLqBdHarXB64XpAe2VCjB7rIRv+mU8tfRWziHRJ5umKsIHN2tLLv6EtMw7WCdP19S0ERVMldNvxYCHnhSQ==", + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/require-in-the-middle/-/require-in-the-middle-8.0.1.tgz", + "integrity": "sha512-QT7FVMXfWOYFbeRBF6nu+I6tr2Tf3u0q8RIEjNob/heKY/nh7drD/k7eeMFmSQgnTtCzLDcCu/XEnpW2wk4xCQ==", "license": "MIT", "dependencies": { "debug": "^4.3.5", - "module-details-from-path": "^1.0.3", - "resolve": "^1.22.8" + "module-details-from-path": "^1.0.3" }, "engines": { - "node": ">=8.6.0" + "node": ">=9.3.0 || >=8.10.0 <9.0.0" } }, "node_modules/resolve": { - "version": "1.22.11", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.11.tgz", - "integrity": "sha512-RfqAvLnMl313r7c9oclB1HhUEAezcpLjz95wFH4LVuhk9JF/r22qmVP9AMmOU4vMX7Q8pN8jwNg/CSpdFnMjTQ==", + "version": "1.22.12", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.12.tgz", + "integrity": "sha512-TyeJ1zif53BPfHootBGwPRYT1RUt6oGWsaQr8UyZW/eAm9bKoijtvruSDEmZHm92CwS9nj7/fWttqPCgzep8CA==", "license": "MIT", "dependencies": { + "es-errors": "^1.3.0", "is-core-module": "^2.16.1", "path-parse": "^1.0.7", "supports-preserve-symlinks-flag": "^1.0.0" @@ -5296,15 +4872,6 @@ "node": ">=8" } }, - "node_modules/retry": { - "version": "0.13.1", - "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", - "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", - "license": "MIT", - "engines": { - "node": ">= 4" - } - }, "node_modules/retry-request": { "version": "7.0.2", "resolved": "https://registry.npmjs.org/retry-request/-/retry-request-7.0.2.tgz", @@ -5320,13 +4887,13 @@ } }, "node_modules/rollup": { - "version": "4.55.2", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.55.2.tgz", - "integrity": "sha512-PggGy4dhwx5qaW+CKBilA/98Ql9keyfnb7lh4SR6shQ91QQQi1ORJ1v4UinkdP2i87OBs9AQFooQylcrrRfIcg==", + "version": "4.62.2", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.62.2.tgz", + "integrity": "sha512-RFnrW4lhXA3s3eqHDZvN654g8OTjzRfqpIRJYczCGB6HzphckVAi/Qh4tbPUbRuDi7s1Llv8g/NspLkttY3gTA==", "dev": true, "license": "MIT", "dependencies": { - "@types/estree": "1.0.8" + "@types/estree": "1.0.9" }, "bin": { "rollup": "dist/bin/rollup" @@ -5336,31 +4903,31 @@ "npm": ">=8.0.0" }, "optionalDependencies": { - "@rollup/rollup-android-arm-eabi": "4.55.2", - "@rollup/rollup-android-arm64": "4.55.2", - "@rollup/rollup-darwin-arm64": "4.55.2", - "@rollup/rollup-darwin-x64": "4.55.2", - "@rollup/rollup-freebsd-arm64": "4.55.2", - "@rollup/rollup-freebsd-x64": "4.55.2", - "@rollup/rollup-linux-arm-gnueabihf": "4.55.2", - "@rollup/rollup-linux-arm-musleabihf": "4.55.2", - "@rollup/rollup-linux-arm64-gnu": "4.55.2", - "@rollup/rollup-linux-arm64-musl": "4.55.2", - "@rollup/rollup-linux-loong64-gnu": "4.55.2", - "@rollup/rollup-linux-loong64-musl": "4.55.2", - "@rollup/rollup-linux-ppc64-gnu": "4.55.2", - "@rollup/rollup-linux-ppc64-musl": "4.55.2", - "@rollup/rollup-linux-riscv64-gnu": "4.55.2", - "@rollup/rollup-linux-riscv64-musl": "4.55.2", - "@rollup/rollup-linux-s390x-gnu": "4.55.2", - "@rollup/rollup-linux-x64-gnu": "4.55.2", - "@rollup/rollup-linux-x64-musl": "4.55.2", - "@rollup/rollup-openbsd-x64": "4.55.2", - "@rollup/rollup-openharmony-arm64": "4.55.2", - "@rollup/rollup-win32-arm64-msvc": "4.55.2", - "@rollup/rollup-win32-ia32-msvc": "4.55.2", - "@rollup/rollup-win32-x64-gnu": "4.55.2", - "@rollup/rollup-win32-x64-msvc": "4.55.2", + "@rollup/rollup-android-arm-eabi": "4.62.2", + "@rollup/rollup-android-arm64": "4.62.2", + "@rollup/rollup-darwin-arm64": "4.62.2", + "@rollup/rollup-darwin-x64": "4.62.2", + "@rollup/rollup-freebsd-arm64": "4.62.2", + "@rollup/rollup-freebsd-x64": "4.62.2", + "@rollup/rollup-linux-arm-gnueabihf": "4.62.2", + "@rollup/rollup-linux-arm-musleabihf": "4.62.2", + "@rollup/rollup-linux-arm64-gnu": "4.62.2", + "@rollup/rollup-linux-arm64-musl": "4.62.2", + "@rollup/rollup-linux-loong64-gnu": "4.62.2", + "@rollup/rollup-linux-loong64-musl": "4.62.2", + "@rollup/rollup-linux-ppc64-gnu": "4.62.2", + "@rollup/rollup-linux-ppc64-musl": "4.62.2", + "@rollup/rollup-linux-riscv64-gnu": "4.62.2", + "@rollup/rollup-linux-riscv64-musl": "4.62.2", + "@rollup/rollup-linux-s390x-gnu": "4.62.2", + "@rollup/rollup-linux-x64-gnu": "4.62.2", + "@rollup/rollup-linux-x64-musl": "4.62.2", + "@rollup/rollup-openbsd-x64": "4.62.2", + "@rollup/rollup-openharmony-arm64": "4.62.2", + "@rollup/rollup-win32-arm64-msvc": "4.62.2", + "@rollup/rollup-win32-ia32-msvc": "4.62.2", + "@rollup/rollup-win32-x64-gnu": "4.62.2", + "@rollup/rollup-win32-x64-msvc": "4.62.2", "fsevents": "~2.3.2" } }, @@ -5385,9 +4952,9 @@ "license": "MIT" }, "node_modules/semver": { - "version": "7.7.3", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.3.tgz", - "integrity": "sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q==", + "version": "7.8.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.8.5.tgz", + "integrity": "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA==", "license": "ISC", "bin": { "semver": "bin/semver.js" @@ -5402,12 +4969,6 @@ "integrity": "sha512-sQTKC1Re/rM6XyFM6fIAGHRPVGvyXfgzIDvzoq608vM+jeyVD0Tu1E6Np0Kc2zAIFWIj963V2800iF/9LPieQw==", "license": "BSD-2-Clause" }, - "node_modules/simple-wcswidth": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/simple-wcswidth/-/simple-wcswidth-1.1.2.tgz", - "integrity": "sha512-j7piyCjAeTDSjzTSQ7DokZtMNwNlEAyxqSZeCS+CXH7fJ4jx3FuJ/mTW3mE+6JLs4VJBbcll0Kjn+KXI5t21Iw==", - "license": "MIT" - }, "node_modules/source-map": { "version": "0.7.6", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.6.tgz", @@ -5547,44 +5108,6 @@ "node": ">=14" } }, - "node_modules/teeny-request/node_modules/agent-base": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", - "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", - "license": "MIT", - "dependencies": { - "debug": "4" - }, - "engines": { - "node": ">= 6.0.0" - } - }, - "node_modules/teeny-request/node_modules/https-proxy-agent": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz", - "integrity": "sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==", - "license": "MIT", - "dependencies": { - "agent-base": "6", - "debug": "4" - }, - "engines": { - "node": ">= 6" - } - }, - "node_modules/teeny-request/node_modules/uuid": { - "version": "9.0.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.1.tgz", - "integrity": "sha512-b+1eJOlsR9K8HJpow9Ok3fiWOWSIcIzXodvv0rQjVoOVNpWMpxf1wZNpt4y9h10odCNrqnYp1OBzRktckBe3sA==", - "funding": [ - "https://github.com/sponsors/broofa", - "https://github.com/sponsors/ctavan" - ], - "license": "MIT", - "bin": { - "uuid": "dist/bin/uuid" - } - }, "node_modules/thenify": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.1.tgz", @@ -5616,14 +5139,14 @@ "license": "MIT" }, "node_modules/tinyglobby": { - "version": "0.2.15", - "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz", - "integrity": "sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==", + "version": "0.2.17", + "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.17.tgz", + "integrity": "sha512-wXR/dYpcqKmfWpEdZjiKJOwCNFndD0DMnrW/cYjVGttEkBfVgcLFHoNrlj47mjOVic9yyNu65alsgF4NQyTa2g==", "dev": true, "license": "MIT", "dependencies": { "fdir": "^6.5.0", - "picomatch": "^4.0.3" + "picomatch": "^4.0.4" }, "engines": { "node": ">=12.0.0" @@ -5758,36 +5281,6 @@ } } }, - "node_modules/tsup/node_modules/chokidar": { - "version": "4.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-4.0.3.tgz", - "integrity": "sha512-Qgzu8kfBvo+cA4962jnP1KkS6Dop5NS6g7R5LFYJr4b8Ub94PPQXUksCw9PvXoeXPRRddRNC5C1JQUR2SMGtnA==", - "dev": true, - "license": "MIT", - "dependencies": { - "readdirp": "^4.0.1" - }, - "engines": { - "node": ">= 14.16.0" - }, - "funding": { - "url": "https://paulmillr.com/funding/" - } - }, - "node_modules/tsup/node_modules/readdirp": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz", - "integrity": "sha512-GDhwkLfywWL2s6vEjyhri+eXmfH6j1L7JE27WhqLeYzoh/A3DBaYGEj2H/HFZCn/kMfim73FXxEJTw06WtxQwg==", - "dev": true, - "license": "MIT", - "engines": { - "node": ">= 14.18.0" - }, - "funding": { - "type": "individual", - "url": "https://paulmillr.com/funding/" - } - }, "node_modules/typescript": { "version": "5.9.3", "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.9.3.tgz", @@ -5803,16 +5296,16 @@ } }, "node_modules/ufo": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/ufo/-/ufo-1.6.3.tgz", - "integrity": "sha512-yDJTmhydvl5lJzBmy/hyOAA0d+aqCBuwl818haVdYCRrWV84o7YyeVm4QlVHStqNrrJSTb6jKuFAVqAFsr+K3Q==", + "version": "1.6.4", + "resolved": "https://registry.npmjs.org/ufo/-/ufo-1.6.4.tgz", + "integrity": "sha512-JFNbkD1Svwe0KvGi8GOeLcP4kAWQ609twvCdcHxq1oSL8svv39ZuSvajcD8B+5D0eL4+s1Is2D/O6KN3qcTeRA==", "dev": true, "license": "MIT" }, "node_modules/undici-types": { - "version": "7.16.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz", - "integrity": "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==", + "version": "7.24.6", + "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.24.6.tgz", + "integrity": "sha512-WRNW+sJgj5OBN4/0JpHFqtqzhpbnV0GuB+OozA9gCL7a993SmU+1JBZCzLNxYsbMfIeDL+lTsphD5jN5N+n0zg==", "license": "MIT" }, "node_modules/util-deprecate": { @@ -5822,16 +5315,16 @@ "license": "MIT" }, "node_modules/uuid": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-10.0.0.tgz", - "integrity": "sha512-8XkAphELsDnEGrDxUOHB3RGvXz6TeuYSGEZBOjtTtPm2lwhGBjLgOzLHB63IUWfBpNucQjND6d3AOudO+H3RWQ==", + "version": "11.1.1", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-11.1.1.tgz", + "integrity": "sha512-vIYxrBCC/N/K+Js3qSN88go7kIfNPssr/hHCesKCQNAjmgvYS2oqr69kIufEG+O4+PfezOH4EbIeHCfFov8ZgQ==", "funding": [ "https://github.com/sponsors/broofa", "https://github.com/sponsors/ctavan" ], "license": "MIT", "bin": { - "uuid": "dist/bin/uuid" + "uuid": "dist/esm/bin/uuid" } }, "node_modules/v8-compile-cache-lib": { @@ -5881,21 +5374,6 @@ "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/wrap-ansi/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "license": "MIT", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", @@ -5911,10 +5389,25 @@ "node": ">=10" } }, + "node_modules/yaml": { + "version": "2.9.0", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.9.0.tgz", + "integrity": "sha512-2AvhNX3mb8zd6Zy7INTtSpl1F15HW6Wnqj0srWlkKLcpYl/gMIMJiyuGq2KeI2YFxUPjdlB+3Lc10seMLtL4cA==", + "license": "ISC", + "bin": { + "yaml": "bin.mjs" + }, + "engines": { + "node": ">= 14.6" + }, + "funding": { + "url": "https://github.com/sponsors/eemeli" + } + }, "node_modules/yargs": { - "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "version": "17.7.3", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.3.tgz", + "integrity": "sha512-GZtjxm/J/4TSxuL3FNYjCmLktBTnIw/rVmKSIyKeYAZpmJB2ig9VauCC5xsa82GNKVKDAqpOn3KVzNt0zmrU0g==", "license": "MIT", "dependencies": { "cliui": "^8.0.1", @@ -5961,23 +5454,13 @@ } }, "node_modules/zod": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.5.tgz", - "integrity": "sha512-k7Nwx6vuWx1IJ9Bjuf4Zt1PEllcwe7cls3VNzm4CQ1/hgtFUK2bRNG3rvnpPUhFjmqJKAKtjV576KnUkHocg/g==", + "version": "4.4.3", + "resolved": "https://registry.npmjs.org/zod/-/zod-4.4.3.tgz", + "integrity": "sha512-ytENFjIJFl2UwYglde2jchW2Hwm4GJFLDiSXWdTrJQBIN9Fcyp7n4DhxJEiWNAJMV1/BqWfW/kkg71UDcHJyTQ==", "license": "MIT", - "peer": true, "funding": { "url": "https://github.com/sponsors/colinhacks" } - }, - "node_modules/zod-to-json-schema": { - "version": "3.25.1", - "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.25.1.tgz", - "integrity": "sha512-pM/SU9d3YAggzi6MtR4h7ruuQlqKtad8e9S0fmxcMi+ueAK5Korys/aWcV9LIIHTVbj01NdzxcnXSN+O74ZIVA==", - "license": "ISC", - "peerDependencies": { - "zod": "^3.25 || ^4" - } } } } diff --git a/package.json b/package.json index c263922..8f8c33c 100644 --- a/package.json +++ b/package.json @@ -49,15 +49,15 @@ }, "dependencies": { "@opentelemetry/api": "^1.9.0", - "@opentelemetry/core": "^2.0.1", - "@opentelemetry/instrumentation-undici": "^0.6.0", + "@opentelemetry/core": "^2.8.0", + "@opentelemetry/instrumentation-undici": "^0.10.0", "@opentelemetry/instrumentation-express": "^0.67.0", "@opentelemetry/instrumentation-http": "^0.219.0", - "@opentelemetry/otlp-transformer": "^0.211.0", - "@opentelemetry/resources": "^2.0.1", - "@opentelemetry/sdk-trace-base": "^2.0.1", - "@traceloop/node-server-sdk": "^0.22.5", - "axios": "^1.13.4", + "@opentelemetry/otlp-transformer": "^0.220.0", + "@opentelemetry/resources": "^2.8.0", + "@opentelemetry/sdk-trace-base": "^2.8.0", + "@traceloop/node-server-sdk": "^0.27.0", + "axios": "^1.18.1", "dotenv": "^17.2.3", "p-limit": "^7.2.0", "shimmer": "^1.2.1" @@ -71,7 +71,7 @@ "@opentelemetry/instrumentation": ">=0.53.0", "@opentelemetry/instrumentation-express": "^0.67.0", "@opentelemetry/instrumentation-http": "^0.219.0", - "@opentelemetry/instrumentation-undici": "^0.6.0", + "@opentelemetry/instrumentation-undici": "^0.10.0", "@prisma/instrumentation": "^5.0.0", "groq-sdk": ">=0.3.0", "openai": "^4.0.0 || ^5.0.0 || ^6.0.0", @@ -122,5 +122,33 @@ "ts-node": "^10.9.2", "tsup": "^8.5.1", "typescript": "^5.9.3" + }, + "overrides": { + "@opentelemetry/core": "^2.8.0", + "@opentelemetry/resources": "^2.8.0", + "@opentelemetry/sdk-trace-base": "^2.8.0", + "@opentelemetry/sdk-trace-node": "^2.8.0", + "@opentelemetry/sdk-metrics": "^2.8.0", + "@opentelemetry/sdk-logs": "^0.220.0", + "@opentelemetry/sdk-node": "^0.220.0", + "@opentelemetry/exporter-trace-otlp-proto": "^0.220.0", + "@opentelemetry/exporter-trace-otlp-grpc": "^0.220.0", + "@opentelemetry/exporter-trace-otlp-http": "^0.220.0", + "@opentelemetry/exporter-metrics-otlp-grpc": "^0.220.0", + "@opentelemetry/exporter-metrics-otlp-http": "^0.220.0", + "@opentelemetry/exporter-metrics-otlp-proto": "^0.220.0", + "@opentelemetry/exporter-logs-otlp-grpc": "^0.220.0", + "@opentelemetry/exporter-logs-otlp-http": "^0.220.0", + "@opentelemetry/exporter-logs-otlp-proto": "^0.220.0", + "@opentelemetry/exporter-prometheus": "^0.220.0", + "@opentelemetry/exporter-zipkin": "^2.8.0", + "@opentelemetry/otlp-exporter-base": "^0.220.0", + "@opentelemetry/otlp-grpc-exporter-base": "^0.220.0", + "@opentelemetry/otlp-transformer": "^0.220.0", + "@opentelemetry/propagator-b3": "^2.8.0", + "@opentelemetry/propagator-jaeger": "^2.8.0", + "@opentelemetry/instrumentation-undici": "^0.10.0", + "uuid": "^11.1.1", + "esbuild": "^0.28.1" } }