@fallom/trace 0.1.10 → 0.1.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.mts +137 -2
- package/dist/index.d.ts +137 -2
- package/dist/index.js +382 -43
- package/dist/index.mjs +378 -43
- package/package.json +3 -1
package/dist/index.d.mts
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import { SpanExporter, ReadableSpan } from '@opentelemetry/sdk-trace-base';
|
|
2
|
+
import { ExportResult } from '@opentelemetry/core';
|
|
3
|
+
|
|
1
4
|
/**
|
|
2
5
|
* Fallom tracing module.
|
|
3
6
|
*
|
|
@@ -222,6 +225,31 @@ declare function wrapAISDK<T extends {
|
|
|
222
225
|
generateObject: T["generateObject"];
|
|
223
226
|
streamObject: T["streamObject"];
|
|
224
227
|
};
|
|
228
|
+
/**
|
|
229
|
+
* Wrap a Mastra agent to automatically trace all generate() calls.
|
|
230
|
+
*
|
|
231
|
+
* @param agent - The Mastra Agent instance
|
|
232
|
+
* @returns The same agent with tracing enabled
|
|
233
|
+
*
|
|
234
|
+
* @example
|
|
235
|
+
* ```typescript
|
|
236
|
+
* import { trace } from "@fallom/trace";
|
|
237
|
+
* import { Agent } from "@mastra/core";
|
|
238
|
+
*
|
|
239
|
+
* await trace.init({ apiKey: "your-key" });
|
|
240
|
+
*
|
|
241
|
+
* const agent = new Agent({ ... });
|
|
242
|
+
* const tracedAgent = trace.wrapMastraAgent(agent);
|
|
243
|
+
*
|
|
244
|
+
* trace.setSession("my-app", "session-123", "user-456");
|
|
245
|
+
* const result = await tracedAgent.generate([{ role: "user", content: "Hello" }]);
|
|
246
|
+
* // ^ Automatically traced!
|
|
247
|
+
* ```
|
|
248
|
+
*/
|
|
249
|
+
declare function wrapMastraAgent<T extends {
|
|
250
|
+
generate: (...args: any[]) => Promise<any>;
|
|
251
|
+
name?: string;
|
|
252
|
+
}>(agent: T): T;
|
|
225
253
|
|
|
226
254
|
declare const trace_clearSession: typeof clearSession;
|
|
227
255
|
declare const trace_getSession: typeof getSession;
|
|
@@ -232,9 +260,10 @@ declare const trace_span: typeof span;
|
|
|
232
260
|
declare const trace_wrapAISDK: typeof wrapAISDK;
|
|
233
261
|
declare const trace_wrapAnthropic: typeof wrapAnthropic;
|
|
234
262
|
declare const trace_wrapGoogleAI: typeof wrapGoogleAI;
|
|
263
|
+
declare const trace_wrapMastraAgent: typeof wrapMastraAgent;
|
|
235
264
|
declare const trace_wrapOpenAI: typeof wrapOpenAI;
|
|
236
265
|
declare namespace trace {
|
|
237
|
-
export { trace_clearSession as clearSession, trace_getSession as getSession, init$3 as init, trace_runWithSession as runWithSession, trace_setSession as setSession, trace_shutdown as shutdown, trace_span as span, trace_wrapAISDK as wrapAISDK, trace_wrapAnthropic as wrapAnthropic, trace_wrapGoogleAI as wrapGoogleAI, trace_wrapOpenAI as wrapOpenAI };
|
|
266
|
+
export { trace_clearSession as clearSession, trace_getSession as getSession, init$3 as init, trace_runWithSession as runWithSession, trace_setSession as setSession, trace_shutdown as shutdown, trace_span as span, trace_wrapAISDK as wrapAISDK, trace_wrapAnthropic as wrapAnthropic, trace_wrapGoogleAI as wrapGoogleAI, trace_wrapMastraAgent as wrapMastraAgent, trace_wrapOpenAI as wrapOpenAI };
|
|
238
267
|
}
|
|
239
268
|
|
|
240
269
|
/**
|
|
@@ -444,6 +473,112 @@ interface InitOptions {
|
|
|
444
473
|
*/
|
|
445
474
|
declare function init(options?: InitOptions): Promise<void>;
|
|
446
475
|
|
|
476
|
+
/**
|
|
477
|
+
* Fallom Exporter for Mastra
|
|
478
|
+
*
|
|
479
|
+
* Custom OpenTelemetry exporter that sends traces from Mastra agents to Fallom.
|
|
480
|
+
* Reads session context from the shared trace module (set via trace.setSession()).
|
|
481
|
+
*
|
|
482
|
+
* Usage with Mastra:
|
|
483
|
+
* ```typescript
|
|
484
|
+
* import { trace, FallomExporter } from "@fallom/trace";
|
|
485
|
+
* import { Mastra } from "@mastra/core/mastra";
|
|
486
|
+
*
|
|
487
|
+
* // Initialize trace module
|
|
488
|
+
* await trace.init({ apiKey: process.env.FALLOM_API_KEY });
|
|
489
|
+
*
|
|
490
|
+
* // Create Mastra with Fallom exporter
|
|
491
|
+
* const mastra = new Mastra({
|
|
492
|
+
* agents: { myAgent },
|
|
493
|
+
* telemetry: {
|
|
494
|
+
* serviceName: "my-agent",
|
|
495
|
+
* enabled: true,
|
|
496
|
+
* export: {
|
|
497
|
+
* type: "custom",
|
|
498
|
+
* exporter: new FallomExporter(),
|
|
499
|
+
* },
|
|
500
|
+
* },
|
|
501
|
+
* });
|
|
502
|
+
*
|
|
503
|
+
* // In your request handler:
|
|
504
|
+
* trace.setSession("my-app", "session-123", "user-456");
|
|
505
|
+
* const result = await mastra.getAgent("myAgent").generate("Hello!");
|
|
506
|
+
* ```
|
|
507
|
+
*/
|
|
508
|
+
|
|
509
|
+
interface FallomExporterOptions {
|
|
510
|
+
/** Fallom API key. Defaults to FALLOM_API_KEY env var. */
|
|
511
|
+
apiKey?: string;
|
|
512
|
+
/** Base URL for traces endpoint (defaults to https://traces.fallom.com) */
|
|
513
|
+
baseUrl?: string;
|
|
514
|
+
/** Enable debug logging */
|
|
515
|
+
debug?: boolean;
|
|
516
|
+
}
|
|
517
|
+
/**
|
|
518
|
+
* Set prompt tracking info.
|
|
519
|
+
* Call this after prompts.get() to track which prompt was used.
|
|
520
|
+
*/
|
|
521
|
+
declare function setMastraPrompt(promptKey: string, version?: number): void;
|
|
522
|
+
/**
|
|
523
|
+
* Set A/B test prompt tracking info.
|
|
524
|
+
* Call this after prompts.getAB() to track which variant was used.
|
|
525
|
+
*/
|
|
526
|
+
declare function setMastraPromptAB(abTestKey: string, variantIndex: number): void;
|
|
527
|
+
/**
|
|
528
|
+
* Clear prompt tracking info.
|
|
529
|
+
*/
|
|
530
|
+
declare function clearMastraPrompt(): void;
|
|
531
|
+
/**
|
|
532
|
+
* OpenTelemetry SpanExporter that sends traces to Fallom.
|
|
533
|
+
*
|
|
534
|
+
* Reads session context from trace.setSession() automatically.
|
|
535
|
+
* Compatible with Mastra's custom exporter interface.
|
|
536
|
+
*/
|
|
537
|
+
declare class FallomExporter implements SpanExporter {
|
|
538
|
+
private apiKey;
|
|
539
|
+
private baseUrl;
|
|
540
|
+
private debug;
|
|
541
|
+
private pendingExports;
|
|
542
|
+
constructor(options?: FallomExporterOptions);
|
|
543
|
+
private log;
|
|
544
|
+
/**
|
|
545
|
+
* Export spans to Fallom.
|
|
546
|
+
*/
|
|
547
|
+
export(spans: ReadableSpan[], resultCallback: (result: ExportResult) => void): void;
|
|
548
|
+
/**
|
|
549
|
+
* Shutdown the exporter, waiting for pending exports.
|
|
550
|
+
*/
|
|
551
|
+
shutdown(): Promise<void>;
|
|
552
|
+
/**
|
|
553
|
+
* Force flush pending exports.
|
|
554
|
+
*/
|
|
555
|
+
forceFlush(): Promise<void>;
|
|
556
|
+
/**
|
|
557
|
+
* Send spans to Fallom's OTLP endpoint.
|
|
558
|
+
*/
|
|
559
|
+
private sendSpans;
|
|
560
|
+
/**
|
|
561
|
+
* Convert OpenTelemetry spans to OTLP JSON format.
|
|
562
|
+
*/
|
|
563
|
+
private spansToOtlpJson;
|
|
564
|
+
/**
|
|
565
|
+
* Convert a single span to OTLP format.
|
|
566
|
+
*/
|
|
567
|
+
private spanToOtlp;
|
|
568
|
+
/**
|
|
569
|
+
* Convert attributes to OTLP format.
|
|
570
|
+
*/
|
|
571
|
+
private attributesToOtlp;
|
|
572
|
+
/**
|
|
573
|
+
* Convert a value to OTLP AnyValue format.
|
|
574
|
+
*/
|
|
575
|
+
private valueToOtlp;
|
|
576
|
+
/**
|
|
577
|
+
* Convert HrTime to nanoseconds string.
|
|
578
|
+
*/
|
|
579
|
+
private hrTimeToNanos;
|
|
580
|
+
}
|
|
581
|
+
|
|
447
582
|
/**
|
|
448
583
|
* Fallom - Model A/B testing, prompt management, and tracing for LLM applications.
|
|
449
584
|
*
|
|
@@ -488,4 +623,4 @@ declare const _default: {
|
|
|
488
623
|
prompts: typeof prompts;
|
|
489
624
|
};
|
|
490
625
|
|
|
491
|
-
export { type InitOptions, type PromptResult, _default as default, init, models, prompts, trace };
|
|
626
|
+
export { FallomExporter, type FallomExporterOptions, type InitOptions, type PromptResult, clearMastraPrompt, _default as default, init, models, prompts, setMastraPrompt, setMastraPromptAB, trace };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import { SpanExporter, ReadableSpan } from '@opentelemetry/sdk-trace-base';
|
|
2
|
+
import { ExportResult } from '@opentelemetry/core';
|
|
3
|
+
|
|
1
4
|
/**
|
|
2
5
|
* Fallom tracing module.
|
|
3
6
|
*
|
|
@@ -222,6 +225,31 @@ declare function wrapAISDK<T extends {
|
|
|
222
225
|
generateObject: T["generateObject"];
|
|
223
226
|
streamObject: T["streamObject"];
|
|
224
227
|
};
|
|
228
|
+
/**
|
|
229
|
+
* Wrap a Mastra agent to automatically trace all generate() calls.
|
|
230
|
+
*
|
|
231
|
+
* @param agent - The Mastra Agent instance
|
|
232
|
+
* @returns The same agent with tracing enabled
|
|
233
|
+
*
|
|
234
|
+
* @example
|
|
235
|
+
* ```typescript
|
|
236
|
+
* import { trace } from "@fallom/trace";
|
|
237
|
+
* import { Agent } from "@mastra/core";
|
|
238
|
+
*
|
|
239
|
+
* await trace.init({ apiKey: "your-key" });
|
|
240
|
+
*
|
|
241
|
+
* const agent = new Agent({ ... });
|
|
242
|
+
* const tracedAgent = trace.wrapMastraAgent(agent);
|
|
243
|
+
*
|
|
244
|
+
* trace.setSession("my-app", "session-123", "user-456");
|
|
245
|
+
* const result = await tracedAgent.generate([{ role: "user", content: "Hello" }]);
|
|
246
|
+
* // ^ Automatically traced!
|
|
247
|
+
* ```
|
|
248
|
+
*/
|
|
249
|
+
declare function wrapMastraAgent<T extends {
|
|
250
|
+
generate: (...args: any[]) => Promise<any>;
|
|
251
|
+
name?: string;
|
|
252
|
+
}>(agent: T): T;
|
|
225
253
|
|
|
226
254
|
declare const trace_clearSession: typeof clearSession;
|
|
227
255
|
declare const trace_getSession: typeof getSession;
|
|
@@ -232,9 +260,10 @@ declare const trace_span: typeof span;
|
|
|
232
260
|
declare const trace_wrapAISDK: typeof wrapAISDK;
|
|
233
261
|
declare const trace_wrapAnthropic: typeof wrapAnthropic;
|
|
234
262
|
declare const trace_wrapGoogleAI: typeof wrapGoogleAI;
|
|
263
|
+
declare const trace_wrapMastraAgent: typeof wrapMastraAgent;
|
|
235
264
|
declare const trace_wrapOpenAI: typeof wrapOpenAI;
|
|
236
265
|
declare namespace trace {
|
|
237
|
-
export { trace_clearSession as clearSession, trace_getSession as getSession, init$3 as init, trace_runWithSession as runWithSession, trace_setSession as setSession, trace_shutdown as shutdown, trace_span as span, trace_wrapAISDK as wrapAISDK, trace_wrapAnthropic as wrapAnthropic, trace_wrapGoogleAI as wrapGoogleAI, trace_wrapOpenAI as wrapOpenAI };
|
|
266
|
+
export { trace_clearSession as clearSession, trace_getSession as getSession, init$3 as init, trace_runWithSession as runWithSession, trace_setSession as setSession, trace_shutdown as shutdown, trace_span as span, trace_wrapAISDK as wrapAISDK, trace_wrapAnthropic as wrapAnthropic, trace_wrapGoogleAI as wrapGoogleAI, trace_wrapMastraAgent as wrapMastraAgent, trace_wrapOpenAI as wrapOpenAI };
|
|
238
267
|
}
|
|
239
268
|
|
|
240
269
|
/**
|
|
@@ -444,6 +473,112 @@ interface InitOptions {
|
|
|
444
473
|
*/
|
|
445
474
|
declare function init(options?: InitOptions): Promise<void>;
|
|
446
475
|
|
|
476
|
+
/**
|
|
477
|
+
* Fallom Exporter for Mastra
|
|
478
|
+
*
|
|
479
|
+
* Custom OpenTelemetry exporter that sends traces from Mastra agents to Fallom.
|
|
480
|
+
* Reads session context from the shared trace module (set via trace.setSession()).
|
|
481
|
+
*
|
|
482
|
+
* Usage with Mastra:
|
|
483
|
+
* ```typescript
|
|
484
|
+
* import { trace, FallomExporter } from "@fallom/trace";
|
|
485
|
+
* import { Mastra } from "@mastra/core/mastra";
|
|
486
|
+
*
|
|
487
|
+
* // Initialize trace module
|
|
488
|
+
* await trace.init({ apiKey: process.env.FALLOM_API_KEY });
|
|
489
|
+
*
|
|
490
|
+
* // Create Mastra with Fallom exporter
|
|
491
|
+
* const mastra = new Mastra({
|
|
492
|
+
* agents: { myAgent },
|
|
493
|
+
* telemetry: {
|
|
494
|
+
* serviceName: "my-agent",
|
|
495
|
+
* enabled: true,
|
|
496
|
+
* export: {
|
|
497
|
+
* type: "custom",
|
|
498
|
+
* exporter: new FallomExporter(),
|
|
499
|
+
* },
|
|
500
|
+
* },
|
|
501
|
+
* });
|
|
502
|
+
*
|
|
503
|
+
* // In your request handler:
|
|
504
|
+
* trace.setSession("my-app", "session-123", "user-456");
|
|
505
|
+
* const result = await mastra.getAgent("myAgent").generate("Hello!");
|
|
506
|
+
* ```
|
|
507
|
+
*/
|
|
508
|
+
|
|
509
|
+
interface FallomExporterOptions {
|
|
510
|
+
/** Fallom API key. Defaults to FALLOM_API_KEY env var. */
|
|
511
|
+
apiKey?: string;
|
|
512
|
+
/** Base URL for traces endpoint (defaults to https://traces.fallom.com) */
|
|
513
|
+
baseUrl?: string;
|
|
514
|
+
/** Enable debug logging */
|
|
515
|
+
debug?: boolean;
|
|
516
|
+
}
|
|
517
|
+
/**
|
|
518
|
+
* Set prompt tracking info.
|
|
519
|
+
* Call this after prompts.get() to track which prompt was used.
|
|
520
|
+
*/
|
|
521
|
+
declare function setMastraPrompt(promptKey: string, version?: number): void;
|
|
522
|
+
/**
|
|
523
|
+
* Set A/B test prompt tracking info.
|
|
524
|
+
* Call this after prompts.getAB() to track which variant was used.
|
|
525
|
+
*/
|
|
526
|
+
declare function setMastraPromptAB(abTestKey: string, variantIndex: number): void;
|
|
527
|
+
/**
|
|
528
|
+
* Clear prompt tracking info.
|
|
529
|
+
*/
|
|
530
|
+
declare function clearMastraPrompt(): void;
|
|
531
|
+
/**
|
|
532
|
+
* OpenTelemetry SpanExporter that sends traces to Fallom.
|
|
533
|
+
*
|
|
534
|
+
* Reads session context from trace.setSession() automatically.
|
|
535
|
+
* Compatible with Mastra's custom exporter interface.
|
|
536
|
+
*/
|
|
537
|
+
declare class FallomExporter implements SpanExporter {
|
|
538
|
+
private apiKey;
|
|
539
|
+
private baseUrl;
|
|
540
|
+
private debug;
|
|
541
|
+
private pendingExports;
|
|
542
|
+
constructor(options?: FallomExporterOptions);
|
|
543
|
+
private log;
|
|
544
|
+
/**
|
|
545
|
+
* Export spans to Fallom.
|
|
546
|
+
*/
|
|
547
|
+
export(spans: ReadableSpan[], resultCallback: (result: ExportResult) => void): void;
|
|
548
|
+
/**
|
|
549
|
+
* Shutdown the exporter, waiting for pending exports.
|
|
550
|
+
*/
|
|
551
|
+
shutdown(): Promise<void>;
|
|
552
|
+
/**
|
|
553
|
+
* Force flush pending exports.
|
|
554
|
+
*/
|
|
555
|
+
forceFlush(): Promise<void>;
|
|
556
|
+
/**
|
|
557
|
+
* Send spans to Fallom's OTLP endpoint.
|
|
558
|
+
*/
|
|
559
|
+
private sendSpans;
|
|
560
|
+
/**
|
|
561
|
+
* Convert OpenTelemetry spans to OTLP JSON format.
|
|
562
|
+
*/
|
|
563
|
+
private spansToOtlpJson;
|
|
564
|
+
/**
|
|
565
|
+
* Convert a single span to OTLP format.
|
|
566
|
+
*/
|
|
567
|
+
private spanToOtlp;
|
|
568
|
+
/**
|
|
569
|
+
* Convert attributes to OTLP format.
|
|
570
|
+
*/
|
|
571
|
+
private attributesToOtlp;
|
|
572
|
+
/**
|
|
573
|
+
* Convert a value to OTLP AnyValue format.
|
|
574
|
+
*/
|
|
575
|
+
private valueToOtlp;
|
|
576
|
+
/**
|
|
577
|
+
* Convert HrTime to nanoseconds string.
|
|
578
|
+
*/
|
|
579
|
+
private hrTimeToNanos;
|
|
580
|
+
}
|
|
581
|
+
|
|
447
582
|
/**
|
|
448
583
|
* Fallom - Model A/B testing, prompt management, and tracing for LLM applications.
|
|
449
584
|
*
|
|
@@ -488,4 +623,4 @@ declare const _default: {
|
|
|
488
623
|
prompts: typeof prompts;
|
|
489
624
|
};
|
|
490
625
|
|
|
491
|
-
export { type InitOptions, type PromptResult, _default as default, init, models, prompts, trace };
|
|
626
|
+
export { FallomExporter, type FallomExporterOptions, type InitOptions, type PromptResult, clearMastraPrompt, _default as default, init, models, prompts, setMastraPrompt, setMastraPromptAB, trace };
|
package/dist/index.js
CHANGED
|
@@ -269,10 +269,14 @@ var init_prompts = __esm({
|
|
|
269
269
|
// src/index.ts
|
|
270
270
|
var index_exports = {};
|
|
271
271
|
__export(index_exports, {
|
|
272
|
+
FallomExporter: () => FallomExporter,
|
|
273
|
+
clearMastraPrompt: () => clearMastraPrompt,
|
|
272
274
|
default: () => index_default,
|
|
273
275
|
init: () => init4,
|
|
274
276
|
models: () => models_exports,
|
|
275
277
|
prompts: () => prompts_exports,
|
|
278
|
+
setMastraPrompt: () => setMastraPrompt,
|
|
279
|
+
setMastraPromptAB: () => setMastraPromptAB,
|
|
276
280
|
trace: () => trace_exports
|
|
277
281
|
});
|
|
278
282
|
module.exports = __toCommonJS(index_exports);
|
|
@@ -290,6 +294,7 @@ __export(trace_exports, {
|
|
|
290
294
|
wrapAISDK: () => wrapAISDK,
|
|
291
295
|
wrapAnthropic: () => wrapAnthropic,
|
|
292
296
|
wrapGoogleAI: () => wrapGoogleAI,
|
|
297
|
+
wrapMastraAgent: () => wrapMastraAgent,
|
|
293
298
|
wrapOpenAI: () => wrapOpenAI
|
|
294
299
|
});
|
|
295
300
|
var import_async_hooks = require("async_hooks");
|
|
@@ -299,7 +304,7 @@ var import_exporter_trace_otlp_http = require("@opentelemetry/exporter-trace-otl
|
|
|
299
304
|
// node_modules/@opentelemetry/resources/build/esm/Resource.js
|
|
300
305
|
var import_api = require("@opentelemetry/api");
|
|
301
306
|
|
|
302
|
-
// node_modules/@opentelemetry/semantic-conventions/build/esm/resource/SemanticResourceAttributes.js
|
|
307
|
+
// node_modules/@opentelemetry/resources/node_modules/@opentelemetry/semantic-conventions/build/esm/resource/SemanticResourceAttributes.js
|
|
303
308
|
var SemanticResourceAttributes = {
|
|
304
309
|
/**
|
|
305
310
|
* Name of the cloud provider.
|
|
@@ -679,35 +684,9 @@ var SemanticResourceAttributes = {
|
|
|
679
684
|
*/
|
|
680
685
|
WEBENGINE_DESCRIPTION: "webengine.description"
|
|
681
686
|
};
|
|
682
|
-
var TelemetrySdkLanguageValues = {
|
|
683
|
-
/** cpp. */
|
|
684
|
-
CPP: "cpp",
|
|
685
|
-
/** dotnet. */
|
|
686
|
-
DOTNET: "dotnet",
|
|
687
|
-
/** erlang. */
|
|
688
|
-
ERLANG: "erlang",
|
|
689
|
-
/** go. */
|
|
690
|
-
GO: "go",
|
|
691
|
-
/** java. */
|
|
692
|
-
JAVA: "java",
|
|
693
|
-
/** nodejs. */
|
|
694
|
-
NODEJS: "nodejs",
|
|
695
|
-
/** php. */
|
|
696
|
-
PHP: "php",
|
|
697
|
-
/** python. */
|
|
698
|
-
PYTHON: "python",
|
|
699
|
-
/** ruby. */
|
|
700
|
-
RUBY: "ruby",
|
|
701
|
-
/** webjs. */
|
|
702
|
-
WEBJS: "webjs"
|
|
703
|
-
};
|
|
704
|
-
|
|
705
|
-
// node_modules/@opentelemetry/core/build/esm/version.js
|
|
706
|
-
var VERSION = "1.19.0";
|
|
707
687
|
|
|
708
|
-
// node_modules/@opentelemetry/
|
|
709
|
-
var
|
|
710
|
-
var SDK_INFO = (_a = {}, _a[SemanticResourceAttributes.TELEMETRY_SDK_NAME] = "opentelemetry", _a[SemanticResourceAttributes.PROCESS_RUNTIME_NAME] = "node", _a[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE] = TelemetrySdkLanguageValues.NODEJS, _a[SemanticResourceAttributes.TELEMETRY_SDK_VERSION] = VERSION, _a);
|
|
688
|
+
// node_modules/@opentelemetry/resources/build/esm/Resource.js
|
|
689
|
+
var import_core = require("@opentelemetry/core");
|
|
711
690
|
|
|
712
691
|
// node_modules/@opentelemetry/resources/build/esm/platform/node/default-service-name.js
|
|
713
692
|
function defaultServiceName() {
|
|
@@ -844,10 +823,10 @@ var Resource = (
|
|
|
844
823
|
(function() {
|
|
845
824
|
function Resource2(attributes, asyncAttributesPromise) {
|
|
846
825
|
var _this = this;
|
|
847
|
-
var
|
|
826
|
+
var _a;
|
|
848
827
|
this._attributes = attributes;
|
|
849
828
|
this.asyncAttributesPending = asyncAttributesPromise != null;
|
|
850
|
-
this._syncAttributes = (
|
|
829
|
+
this._syncAttributes = (_a = this._attributes) !== null && _a !== void 0 ? _a : {};
|
|
851
830
|
this._asyncAttributesPromise = asyncAttributesPromise === null || asyncAttributesPromise === void 0 ? void 0 : asyncAttributesPromise.then(function(asyncAttributes) {
|
|
852
831
|
_this._attributes = Object.assign({}, _this._attributes, asyncAttributes);
|
|
853
832
|
_this.asyncAttributesPending = false;
|
|
@@ -862,30 +841,30 @@ var Resource = (
|
|
|
862
841
|
return Resource2.EMPTY;
|
|
863
842
|
};
|
|
864
843
|
Resource2.default = function() {
|
|
865
|
-
var
|
|
866
|
-
return new Resource2((
|
|
844
|
+
var _a;
|
|
845
|
+
return new Resource2((_a = {}, _a[SemanticResourceAttributes.SERVICE_NAME] = defaultServiceName(), _a[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE] = import_core.SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE], _a[SemanticResourceAttributes.TELEMETRY_SDK_NAME] = import_core.SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_NAME], _a[SemanticResourceAttributes.TELEMETRY_SDK_VERSION] = import_core.SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_VERSION], _a));
|
|
867
846
|
};
|
|
868
847
|
Object.defineProperty(Resource2.prototype, "attributes", {
|
|
869
848
|
get: function() {
|
|
870
|
-
var
|
|
849
|
+
var _a;
|
|
871
850
|
if (this.asyncAttributesPending) {
|
|
872
851
|
import_api.diag.error("Accessing resource attributes before async attributes settled");
|
|
873
852
|
}
|
|
874
|
-
return (
|
|
853
|
+
return (_a = this._attributes) !== null && _a !== void 0 ? _a : {};
|
|
875
854
|
},
|
|
876
855
|
enumerable: false,
|
|
877
856
|
configurable: true
|
|
878
857
|
});
|
|
879
858
|
Resource2.prototype.waitForAsyncAttributes = function() {
|
|
880
859
|
return __awaiter(this, void 0, void 0, function() {
|
|
881
|
-
return __generator(this, function(
|
|
882
|
-
switch (
|
|
860
|
+
return __generator(this, function(_a) {
|
|
861
|
+
switch (_a.label) {
|
|
883
862
|
case 0:
|
|
884
863
|
if (!this.asyncAttributesPending) return [3, 2];
|
|
885
864
|
return [4, this._asyncAttributesPromise];
|
|
886
865
|
case 1:
|
|
887
|
-
|
|
888
|
-
|
|
866
|
+
_a.sent();
|
|
867
|
+
_a.label = 2;
|
|
889
868
|
case 2:
|
|
890
869
|
return [
|
|
891
870
|
2
|
|
@@ -897,19 +876,19 @@ var Resource = (
|
|
|
897
876
|
};
|
|
898
877
|
Resource2.prototype.merge = function(other) {
|
|
899
878
|
var _this = this;
|
|
900
|
-
var
|
|
879
|
+
var _a;
|
|
901
880
|
if (!other)
|
|
902
881
|
return this;
|
|
903
|
-
var mergedSyncAttributes = __assign(__assign({}, this._syncAttributes), (
|
|
882
|
+
var mergedSyncAttributes = __assign(__assign({}, this._syncAttributes), (_a = other._syncAttributes) !== null && _a !== void 0 ? _a : other.attributes);
|
|
904
883
|
if (!this._asyncAttributesPromise && !other._asyncAttributesPromise) {
|
|
905
884
|
return new Resource2(mergedSyncAttributes);
|
|
906
885
|
}
|
|
907
886
|
var mergedAttributesPromise = Promise.all([
|
|
908
887
|
this._asyncAttributesPromise,
|
|
909
888
|
other._asyncAttributesPromise
|
|
910
|
-
]).then(function(
|
|
889
|
+
]).then(function(_a2) {
|
|
911
890
|
var _b;
|
|
912
|
-
var _c = __read(
|
|
891
|
+
var _c = __read(_a2, 2), thisAsyncAttributes = _c[0], otherAsyncAttributes = _c[1];
|
|
913
892
|
return __assign(__assign(__assign(__assign({}, _this._syncAttributes), thisAsyncAttributes), (_b = other._syncAttributes) !== null && _b !== void 0 ? _b : other.attributes), otherAsyncAttributes);
|
|
914
893
|
});
|
|
915
894
|
return new Resource2(mergedSyncAttributes, mergedAttributesPromise);
|
|
@@ -1893,6 +1872,127 @@ function createStreamObjectWrapper(aiModule) {
|
|
|
1893
1872
|
return result;
|
|
1894
1873
|
};
|
|
1895
1874
|
}
|
|
1875
|
+
function wrapMastraAgent(agent) {
|
|
1876
|
+
const originalGenerate = agent.generate.bind(agent);
|
|
1877
|
+
const agentName = agent.name || "MastraAgent";
|
|
1878
|
+
agent.generate = async function(...args) {
|
|
1879
|
+
const ctx = sessionStorage.getStore() || fallbackSession;
|
|
1880
|
+
if (!ctx || !initialized2) {
|
|
1881
|
+
return originalGenerate(...args);
|
|
1882
|
+
}
|
|
1883
|
+
let promptCtx = null;
|
|
1884
|
+
try {
|
|
1885
|
+
const { getPromptContext: getPromptContext2 } = await Promise.resolve().then(() => (init_prompts(), prompts_exports));
|
|
1886
|
+
promptCtx = getPromptContext2();
|
|
1887
|
+
} catch {
|
|
1888
|
+
}
|
|
1889
|
+
const traceId = generateHexId(32);
|
|
1890
|
+
const spanId = generateHexId(16);
|
|
1891
|
+
const startTime = Date.now();
|
|
1892
|
+
const messages = args[0] || [];
|
|
1893
|
+
try {
|
|
1894
|
+
const result = await originalGenerate(...args);
|
|
1895
|
+
const endTime = Date.now();
|
|
1896
|
+
const model = result?.model?.modelId || "unknown";
|
|
1897
|
+
const toolCalls = [];
|
|
1898
|
+
if (result?.steps?.length) {
|
|
1899
|
+
for (const step of result.steps) {
|
|
1900
|
+
if (step.toolCalls?.length) {
|
|
1901
|
+
for (let i = 0; i < step.toolCalls.length; i++) {
|
|
1902
|
+
const tc = step.toolCalls[i];
|
|
1903
|
+
const tr = step.toolResults?.[i];
|
|
1904
|
+
toolCalls.push({
|
|
1905
|
+
name: tc.toolName,
|
|
1906
|
+
arguments: tc.args,
|
|
1907
|
+
result: tr?.result
|
|
1908
|
+
});
|
|
1909
|
+
}
|
|
1910
|
+
}
|
|
1911
|
+
}
|
|
1912
|
+
}
|
|
1913
|
+
const attributes = {
|
|
1914
|
+
"gen_ai.system": "Mastra",
|
|
1915
|
+
"gen_ai.request.model": model,
|
|
1916
|
+
"gen_ai.response.model": model,
|
|
1917
|
+
"fallom.source": "mastra-agent",
|
|
1918
|
+
"llm.request.type": "chat"
|
|
1919
|
+
};
|
|
1920
|
+
if (Array.isArray(messages)) {
|
|
1921
|
+
messages.forEach((msg, i) => {
|
|
1922
|
+
attributes[`gen_ai.prompt.${i}.role`] = msg.role || "user";
|
|
1923
|
+
attributes[`gen_ai.prompt.${i}.content`] = typeof msg.content === "string" ? msg.content : JSON.stringify(msg.content);
|
|
1924
|
+
});
|
|
1925
|
+
}
|
|
1926
|
+
if (result?.text) {
|
|
1927
|
+
attributes["gen_ai.completion.0.role"] = "assistant";
|
|
1928
|
+
attributes["gen_ai.completion.0.content"] = result.text;
|
|
1929
|
+
attributes["gen_ai.completion.0.finish_reason"] = "stop";
|
|
1930
|
+
}
|
|
1931
|
+
if (toolCalls.length > 0) {
|
|
1932
|
+
attributes["fallom.tool_calls"] = JSON.stringify(toolCalls);
|
|
1933
|
+
toolCalls.forEach((tc, i) => {
|
|
1934
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.name`] = tc.name;
|
|
1935
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.type`] = "function";
|
|
1936
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.arguments`] = JSON.stringify(tc.arguments);
|
|
1937
|
+
});
|
|
1938
|
+
}
|
|
1939
|
+
if (result?.usage) {
|
|
1940
|
+
attributes["gen_ai.usage.prompt_tokens"] = result.usage.promptTokens;
|
|
1941
|
+
attributes["gen_ai.usage.completion_tokens"] = result.usage.completionTokens;
|
|
1942
|
+
attributes["llm.usage.total_tokens"] = result.usage.totalTokens;
|
|
1943
|
+
}
|
|
1944
|
+
const traceData = {
|
|
1945
|
+
config_key: ctx.configKey,
|
|
1946
|
+
session_id: ctx.sessionId,
|
|
1947
|
+
customer_id: ctx.customerId,
|
|
1948
|
+
trace_id: traceId,
|
|
1949
|
+
span_id: spanId,
|
|
1950
|
+
name: `mastra.${agentName}.generate`,
|
|
1951
|
+
kind: "client",
|
|
1952
|
+
model,
|
|
1953
|
+
start_time: new Date(startTime).toISOString(),
|
|
1954
|
+
end_time: new Date(endTime).toISOString(),
|
|
1955
|
+
duration_ms: endTime - startTime,
|
|
1956
|
+
status: "OK",
|
|
1957
|
+
prompt_tokens: result?.usage?.promptTokens,
|
|
1958
|
+
completion_tokens: result?.usage?.completionTokens,
|
|
1959
|
+
total_tokens: result?.usage?.totalTokens,
|
|
1960
|
+
attributes,
|
|
1961
|
+
prompt_key: promptCtx?.promptKey,
|
|
1962
|
+
prompt_version: promptCtx?.promptVersion,
|
|
1963
|
+
prompt_ab_test_key: promptCtx?.abTestKey,
|
|
1964
|
+
prompt_variant_index: promptCtx?.variantIndex
|
|
1965
|
+
};
|
|
1966
|
+
sendTrace(traceData).catch(() => {
|
|
1967
|
+
});
|
|
1968
|
+
return result;
|
|
1969
|
+
} catch (error) {
|
|
1970
|
+
const endTime = Date.now();
|
|
1971
|
+
const traceData = {
|
|
1972
|
+
config_key: ctx.configKey,
|
|
1973
|
+
session_id: ctx.sessionId,
|
|
1974
|
+
customer_id: ctx.customerId,
|
|
1975
|
+
trace_id: traceId,
|
|
1976
|
+
span_id: spanId,
|
|
1977
|
+
name: `mastra.${agentName}.generate`,
|
|
1978
|
+
kind: "client",
|
|
1979
|
+
start_time: new Date(startTime).toISOString(),
|
|
1980
|
+
end_time: new Date(endTime).toISOString(),
|
|
1981
|
+
duration_ms: endTime - startTime,
|
|
1982
|
+
status: "ERROR",
|
|
1983
|
+
error_message: error instanceof Error ? error.message : String(error),
|
|
1984
|
+
prompt_key: promptCtx?.promptKey,
|
|
1985
|
+
prompt_version: promptCtx?.promptVersion,
|
|
1986
|
+
prompt_ab_test_key: promptCtx?.abTestKey,
|
|
1987
|
+
prompt_variant_index: promptCtx?.variantIndex
|
|
1988
|
+
};
|
|
1989
|
+
sendTrace(traceData).catch(() => {
|
|
1990
|
+
});
|
|
1991
|
+
throw error;
|
|
1992
|
+
}
|
|
1993
|
+
};
|
|
1994
|
+
return agent;
|
|
1995
|
+
}
|
|
1896
1996
|
|
|
1897
1997
|
// src/models.ts
|
|
1898
1998
|
var models_exports = {};
|
|
@@ -2162,6 +2262,241 @@ async function init4(options = {}) {
|
|
|
2162
2262
|
});
|
|
2163
2263
|
}
|
|
2164
2264
|
|
|
2265
|
+
// src/mastra.ts
|
|
2266
|
+
var import_core2 = require("@opentelemetry/core");
|
|
2267
|
+
var promptContext2 = {};
|
|
2268
|
+
function setMastraPrompt(promptKey, version) {
|
|
2269
|
+
promptContext2 = {
|
|
2270
|
+
promptKey,
|
|
2271
|
+
promptVersion: version,
|
|
2272
|
+
promptAbTestKey: void 0,
|
|
2273
|
+
promptVariantIndex: void 0
|
|
2274
|
+
};
|
|
2275
|
+
}
|
|
2276
|
+
function setMastraPromptAB(abTestKey, variantIndex) {
|
|
2277
|
+
promptContext2 = {
|
|
2278
|
+
promptKey: void 0,
|
|
2279
|
+
promptVersion: void 0,
|
|
2280
|
+
promptAbTestKey: abTestKey,
|
|
2281
|
+
promptVariantIndex: variantIndex
|
|
2282
|
+
};
|
|
2283
|
+
}
|
|
2284
|
+
function clearMastraPrompt() {
|
|
2285
|
+
promptContext2 = {};
|
|
2286
|
+
}
|
|
2287
|
+
var FallomExporter = class {
|
|
2288
|
+
constructor(options = {}) {
|
|
2289
|
+
this.pendingExports = [];
|
|
2290
|
+
this.apiKey = options.apiKey ?? process.env.FALLOM_API_KEY ?? "";
|
|
2291
|
+
this.baseUrl = options.baseUrl ?? "https://traces.fallom.com";
|
|
2292
|
+
this.debug = options.debug ?? false;
|
|
2293
|
+
console.log("[FallomExporter] Constructor called, debug:", this.debug);
|
|
2294
|
+
console.log("[FallomExporter] API key present:", !!this.apiKey);
|
|
2295
|
+
console.log("[FallomExporter] Base URL:", this.baseUrl);
|
|
2296
|
+
if (!this.apiKey) {
|
|
2297
|
+
console.warn(
|
|
2298
|
+
"[FallomExporter] No API key provided. Set FALLOM_API_KEY env var or pass apiKey option."
|
|
2299
|
+
);
|
|
2300
|
+
}
|
|
2301
|
+
}
|
|
2302
|
+
log(...args) {
|
|
2303
|
+
if (this.debug) {
|
|
2304
|
+
console.log("[FallomExporter]", ...args);
|
|
2305
|
+
}
|
|
2306
|
+
}
|
|
2307
|
+
/**
|
|
2308
|
+
* Export spans to Fallom.
|
|
2309
|
+
*/
|
|
2310
|
+
export(spans, resultCallback) {
|
|
2311
|
+
if (spans.length === 0) {
|
|
2312
|
+
resultCallback({ code: import_core2.ExportResultCode.SUCCESS });
|
|
2313
|
+
return;
|
|
2314
|
+
}
|
|
2315
|
+
this.log(`Exporting ${spans.length} spans...`);
|
|
2316
|
+
if (this.debug) {
|
|
2317
|
+
for (const span2 of spans) {
|
|
2318
|
+
this.log(` - ${span2.name}`, {
|
|
2319
|
+
attributes: Object.fromEntries(
|
|
2320
|
+
Object.entries(span2.attributes).filter(
|
|
2321
|
+
([k]) => k.startsWith("gen_ai") || k.startsWith("llm")
|
|
2322
|
+
)
|
|
2323
|
+
)
|
|
2324
|
+
});
|
|
2325
|
+
}
|
|
2326
|
+
}
|
|
2327
|
+
const exportPromise = this.sendSpans(spans).then(() => {
|
|
2328
|
+
this.log("Export successful");
|
|
2329
|
+
resultCallback({ code: import_core2.ExportResultCode.SUCCESS });
|
|
2330
|
+
}).catch((error) => {
|
|
2331
|
+
console.error("[FallomExporter] Export failed:", error);
|
|
2332
|
+
resultCallback({
|
|
2333
|
+
code: import_core2.ExportResultCode.FAILED,
|
|
2334
|
+
error: error instanceof Error ? error : new Error(String(error))
|
|
2335
|
+
});
|
|
2336
|
+
});
|
|
2337
|
+
this.pendingExports.push(exportPromise);
|
|
2338
|
+
}
|
|
2339
|
+
/**
|
|
2340
|
+
* Shutdown the exporter, waiting for pending exports.
|
|
2341
|
+
*/
|
|
2342
|
+
async shutdown() {
|
|
2343
|
+
await Promise.all(this.pendingExports);
|
|
2344
|
+
this.pendingExports = [];
|
|
2345
|
+
}
|
|
2346
|
+
/**
|
|
2347
|
+
* Force flush pending exports.
|
|
2348
|
+
*/
|
|
2349
|
+
async forceFlush() {
|
|
2350
|
+
await Promise.all(this.pendingExports);
|
|
2351
|
+
}
|
|
2352
|
+
/**
|
|
2353
|
+
* Send spans to Fallom's OTLP endpoint.
|
|
2354
|
+
*/
|
|
2355
|
+
async sendSpans(spans) {
|
|
2356
|
+
const session = getSession();
|
|
2357
|
+
const resourceSpans = this.spansToOtlpJson(spans);
|
|
2358
|
+
const headers = {
|
|
2359
|
+
"Content-Type": "application/json",
|
|
2360
|
+
Authorization: `Bearer ${this.apiKey}`
|
|
2361
|
+
};
|
|
2362
|
+
if (session?.configKey) {
|
|
2363
|
+
headers["X-Fallom-Config-Key"] = session.configKey;
|
|
2364
|
+
}
|
|
2365
|
+
if (session?.sessionId) {
|
|
2366
|
+
headers["X-Fallom-Session-Id"] = session.sessionId;
|
|
2367
|
+
}
|
|
2368
|
+
if (session?.customerId) {
|
|
2369
|
+
headers["X-Fallom-Customer-Id"] = session.customerId;
|
|
2370
|
+
}
|
|
2371
|
+
if (promptContext2.promptKey) {
|
|
2372
|
+
headers["X-Fallom-Prompt-Key"] = promptContext2.promptKey;
|
|
2373
|
+
}
|
|
2374
|
+
if (promptContext2.promptVersion !== void 0) {
|
|
2375
|
+
headers["X-Fallom-Prompt-Version"] = String(promptContext2.promptVersion);
|
|
2376
|
+
}
|
|
2377
|
+
if (promptContext2.promptAbTestKey) {
|
|
2378
|
+
headers["X-Fallom-Prompt-AB-Test"] = promptContext2.promptAbTestKey;
|
|
2379
|
+
}
|
|
2380
|
+
if (promptContext2.promptVariantIndex !== void 0) {
|
|
2381
|
+
headers["X-Fallom-Prompt-Variant"] = String(
|
|
2382
|
+
promptContext2.promptVariantIndex
|
|
2383
|
+
);
|
|
2384
|
+
}
|
|
2385
|
+
const endpoint = `${this.baseUrl}/v1/traces`;
|
|
2386
|
+
this.log("Sending to", endpoint);
|
|
2387
|
+
this.log("Headers:", {
|
|
2388
|
+
...headers,
|
|
2389
|
+
Authorization: "Bearer ***"
|
|
2390
|
+
});
|
|
2391
|
+
const response = await fetch(endpoint, {
|
|
2392
|
+
method: "POST",
|
|
2393
|
+
headers,
|
|
2394
|
+
body: JSON.stringify({ resourceSpans })
|
|
2395
|
+
});
|
|
2396
|
+
if (!response.ok) {
|
|
2397
|
+
const text = await response.text();
|
|
2398
|
+
throw new Error(`Failed to export: ${response.status} ${text}`);
|
|
2399
|
+
}
|
|
2400
|
+
}
|
|
2401
|
+
/**
|
|
2402
|
+
* Convert OpenTelemetry spans to OTLP JSON format.
|
|
2403
|
+
*/
|
|
2404
|
+
spansToOtlpJson(spans) {
|
|
2405
|
+
const resourceMap = /* @__PURE__ */ new Map();
|
|
2406
|
+
for (const span2 of spans) {
|
|
2407
|
+
const resourceKey = JSON.stringify(span2.resource.attributes);
|
|
2408
|
+
if (!resourceMap.has(resourceKey)) {
|
|
2409
|
+
resourceMap.set(resourceKey, []);
|
|
2410
|
+
}
|
|
2411
|
+
resourceMap.get(resourceKey).push(span2);
|
|
2412
|
+
}
|
|
2413
|
+
const resourceSpans = [];
|
|
2414
|
+
for (const [_resourceKey, resourceSpanList] of resourceMap) {
|
|
2415
|
+
const firstSpan = resourceSpanList[0];
|
|
2416
|
+
resourceSpans.push({
|
|
2417
|
+
resource: {
|
|
2418
|
+
attributes: this.attributesToOtlp(firstSpan.resource.attributes)
|
|
2419
|
+
},
|
|
2420
|
+
scopeSpans: [
|
|
2421
|
+
{
|
|
2422
|
+
scope: {
|
|
2423
|
+
name: firstSpan.instrumentationLibrary.name,
|
|
2424
|
+
version: firstSpan.instrumentationLibrary.version
|
|
2425
|
+
},
|
|
2426
|
+
spans: resourceSpanList.map((span2) => this.spanToOtlp(span2))
|
|
2427
|
+
}
|
|
2428
|
+
]
|
|
2429
|
+
});
|
|
2430
|
+
}
|
|
2431
|
+
return resourceSpans;
|
|
2432
|
+
}
|
|
2433
|
+
/**
|
|
2434
|
+
* Convert a single span to OTLP format.
|
|
2435
|
+
*/
|
|
2436
|
+
spanToOtlp(span2) {
|
|
2437
|
+
return {
|
|
2438
|
+
traceId: span2.spanContext().traceId,
|
|
2439
|
+
spanId: span2.spanContext().spanId,
|
|
2440
|
+
parentSpanId: span2.parentSpanId,
|
|
2441
|
+
name: span2.name,
|
|
2442
|
+
kind: span2.kind,
|
|
2443
|
+
startTimeUnixNano: this.hrTimeToNanos(span2.startTime),
|
|
2444
|
+
endTimeUnixNano: this.hrTimeToNanos(span2.endTime),
|
|
2445
|
+
attributes: this.attributesToOtlp(span2.attributes),
|
|
2446
|
+
status: {
|
|
2447
|
+
code: span2.status.code,
|
|
2448
|
+
message: span2.status.message
|
|
2449
|
+
},
|
|
2450
|
+
events: span2.events.map((event) => ({
|
|
2451
|
+
timeUnixNano: this.hrTimeToNanos(event.time),
|
|
2452
|
+
name: event.name,
|
|
2453
|
+
attributes: this.attributesToOtlp(event.attributes || {})
|
|
2454
|
+
}))
|
|
2455
|
+
};
|
|
2456
|
+
}
|
|
2457
|
+
/**
|
|
2458
|
+
* Convert attributes to OTLP format.
|
|
2459
|
+
*/
|
|
2460
|
+
attributesToOtlp(attrs) {
|
|
2461
|
+
return Object.entries(attrs).map(([key, value]) => ({
|
|
2462
|
+
key,
|
|
2463
|
+
value: this.valueToOtlp(value)
|
|
2464
|
+
}));
|
|
2465
|
+
}
|
|
2466
|
+
/**
|
|
2467
|
+
* Convert a value to OTLP AnyValue format.
|
|
2468
|
+
*/
|
|
2469
|
+
valueToOtlp(value) {
|
|
2470
|
+
if (typeof value === "string") {
|
|
2471
|
+
return { stringValue: value };
|
|
2472
|
+
}
|
|
2473
|
+
if (typeof value === "number") {
|
|
2474
|
+
if (Number.isInteger(value)) {
|
|
2475
|
+
return { intValue: value };
|
|
2476
|
+
}
|
|
2477
|
+
return { doubleValue: value };
|
|
2478
|
+
}
|
|
2479
|
+
if (typeof value === "boolean") {
|
|
2480
|
+
return { boolValue: value };
|
|
2481
|
+
}
|
|
2482
|
+
if (Array.isArray(value)) {
|
|
2483
|
+
return {
|
|
2484
|
+
arrayValue: {
|
|
2485
|
+
values: value.map((v) => this.valueToOtlp(v))
|
|
2486
|
+
}
|
|
2487
|
+
};
|
|
2488
|
+
}
|
|
2489
|
+
return { stringValue: String(value) };
|
|
2490
|
+
}
|
|
2491
|
+
/**
|
|
2492
|
+
* Convert HrTime to nanoseconds string.
|
|
2493
|
+
*/
|
|
2494
|
+
hrTimeToNanos(hrTime) {
|
|
2495
|
+
const [seconds, nanos] = hrTime;
|
|
2496
|
+
return String(BigInt(seconds) * BigInt(1e9) + BigInt(nanos));
|
|
2497
|
+
}
|
|
2498
|
+
};
|
|
2499
|
+
|
|
2165
2500
|
// src/index.ts
|
|
2166
2501
|
init_prompts();
|
|
2167
2502
|
var index_default = {
|
|
@@ -2172,8 +2507,12 @@ var index_default = {
|
|
|
2172
2507
|
};
|
|
2173
2508
|
// Annotate the CommonJS export names for ESM import in node:
|
|
2174
2509
|
0 && (module.exports = {
|
|
2510
|
+
FallomExporter,
|
|
2511
|
+
clearMastraPrompt,
|
|
2175
2512
|
init,
|
|
2176
2513
|
models,
|
|
2177
2514
|
prompts,
|
|
2515
|
+
setMastraPrompt,
|
|
2516
|
+
setMastraPromptAB,
|
|
2178
2517
|
trace
|
|
2179
2518
|
});
|
package/dist/index.mjs
CHANGED
|
@@ -17,6 +17,7 @@ __export(trace_exports, {
|
|
|
17
17
|
wrapAISDK: () => wrapAISDK,
|
|
18
18
|
wrapAnthropic: () => wrapAnthropic,
|
|
19
19
|
wrapGoogleAI: () => wrapGoogleAI,
|
|
20
|
+
wrapMastraAgent: () => wrapMastraAgent,
|
|
20
21
|
wrapOpenAI: () => wrapOpenAI
|
|
21
22
|
});
|
|
22
23
|
import { AsyncLocalStorage } from "async_hooks";
|
|
@@ -26,7 +27,7 @@ import { OTLPTraceExporter } from "@opentelemetry/exporter-trace-otlp-http";
|
|
|
26
27
|
// node_modules/@opentelemetry/resources/build/esm/Resource.js
|
|
27
28
|
import { diag } from "@opentelemetry/api";
|
|
28
29
|
|
|
29
|
-
// node_modules/@opentelemetry/semantic-conventions/build/esm/resource/SemanticResourceAttributes.js
|
|
30
|
+
// node_modules/@opentelemetry/resources/node_modules/@opentelemetry/semantic-conventions/build/esm/resource/SemanticResourceAttributes.js
|
|
30
31
|
var SemanticResourceAttributes = {
|
|
31
32
|
/**
|
|
32
33
|
* Name of the cloud provider.
|
|
@@ -406,35 +407,9 @@ var SemanticResourceAttributes = {
|
|
|
406
407
|
*/
|
|
407
408
|
WEBENGINE_DESCRIPTION: "webengine.description"
|
|
408
409
|
};
|
|
409
|
-
var TelemetrySdkLanguageValues = {
|
|
410
|
-
/** cpp. */
|
|
411
|
-
CPP: "cpp",
|
|
412
|
-
/** dotnet. */
|
|
413
|
-
DOTNET: "dotnet",
|
|
414
|
-
/** erlang. */
|
|
415
|
-
ERLANG: "erlang",
|
|
416
|
-
/** go. */
|
|
417
|
-
GO: "go",
|
|
418
|
-
/** java. */
|
|
419
|
-
JAVA: "java",
|
|
420
|
-
/** nodejs. */
|
|
421
|
-
NODEJS: "nodejs",
|
|
422
|
-
/** php. */
|
|
423
|
-
PHP: "php",
|
|
424
|
-
/** python. */
|
|
425
|
-
PYTHON: "python",
|
|
426
|
-
/** ruby. */
|
|
427
|
-
RUBY: "ruby",
|
|
428
|
-
/** webjs. */
|
|
429
|
-
WEBJS: "webjs"
|
|
430
|
-
};
|
|
431
|
-
|
|
432
|
-
// node_modules/@opentelemetry/core/build/esm/version.js
|
|
433
|
-
var VERSION = "1.19.0";
|
|
434
410
|
|
|
435
|
-
// node_modules/@opentelemetry/
|
|
436
|
-
|
|
437
|
-
var SDK_INFO = (_a = {}, _a[SemanticResourceAttributes.TELEMETRY_SDK_NAME] = "opentelemetry", _a[SemanticResourceAttributes.PROCESS_RUNTIME_NAME] = "node", _a[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE] = TelemetrySdkLanguageValues.NODEJS, _a[SemanticResourceAttributes.TELEMETRY_SDK_VERSION] = VERSION, _a);
|
|
411
|
+
// node_modules/@opentelemetry/resources/build/esm/Resource.js
|
|
412
|
+
import { SDK_INFO } from "@opentelemetry/core";
|
|
438
413
|
|
|
439
414
|
// node_modules/@opentelemetry/resources/build/esm/platform/node/default-service-name.js
|
|
440
415
|
function defaultServiceName() {
|
|
@@ -571,10 +546,10 @@ var Resource = (
|
|
|
571
546
|
(function() {
|
|
572
547
|
function Resource2(attributes, asyncAttributesPromise) {
|
|
573
548
|
var _this = this;
|
|
574
|
-
var
|
|
549
|
+
var _a;
|
|
575
550
|
this._attributes = attributes;
|
|
576
551
|
this.asyncAttributesPending = asyncAttributesPromise != null;
|
|
577
|
-
this._syncAttributes = (
|
|
552
|
+
this._syncAttributes = (_a = this._attributes) !== null && _a !== void 0 ? _a : {};
|
|
578
553
|
this._asyncAttributesPromise = asyncAttributesPromise === null || asyncAttributesPromise === void 0 ? void 0 : asyncAttributesPromise.then(function(asyncAttributes) {
|
|
579
554
|
_this._attributes = Object.assign({}, _this._attributes, asyncAttributes);
|
|
580
555
|
_this.asyncAttributesPending = false;
|
|
@@ -589,30 +564,30 @@ var Resource = (
|
|
|
589
564
|
return Resource2.EMPTY;
|
|
590
565
|
};
|
|
591
566
|
Resource2.default = function() {
|
|
592
|
-
var
|
|
593
|
-
return new Resource2((
|
|
567
|
+
var _a;
|
|
568
|
+
return new Resource2((_a = {}, _a[SemanticResourceAttributes.SERVICE_NAME] = defaultServiceName(), _a[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE] = SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_LANGUAGE], _a[SemanticResourceAttributes.TELEMETRY_SDK_NAME] = SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_NAME], _a[SemanticResourceAttributes.TELEMETRY_SDK_VERSION] = SDK_INFO[SemanticResourceAttributes.TELEMETRY_SDK_VERSION], _a));
|
|
594
569
|
};
|
|
595
570
|
Object.defineProperty(Resource2.prototype, "attributes", {
|
|
596
571
|
get: function() {
|
|
597
|
-
var
|
|
572
|
+
var _a;
|
|
598
573
|
if (this.asyncAttributesPending) {
|
|
599
574
|
diag.error("Accessing resource attributes before async attributes settled");
|
|
600
575
|
}
|
|
601
|
-
return (
|
|
576
|
+
return (_a = this._attributes) !== null && _a !== void 0 ? _a : {};
|
|
602
577
|
},
|
|
603
578
|
enumerable: false,
|
|
604
579
|
configurable: true
|
|
605
580
|
});
|
|
606
581
|
Resource2.prototype.waitForAsyncAttributes = function() {
|
|
607
582
|
return __awaiter(this, void 0, void 0, function() {
|
|
608
|
-
return __generator(this, function(
|
|
609
|
-
switch (
|
|
583
|
+
return __generator(this, function(_a) {
|
|
584
|
+
switch (_a.label) {
|
|
610
585
|
case 0:
|
|
611
586
|
if (!this.asyncAttributesPending) return [3, 2];
|
|
612
587
|
return [4, this._asyncAttributesPromise];
|
|
613
588
|
case 1:
|
|
614
|
-
|
|
615
|
-
|
|
589
|
+
_a.sent();
|
|
590
|
+
_a.label = 2;
|
|
616
591
|
case 2:
|
|
617
592
|
return [
|
|
618
593
|
2
|
|
@@ -624,19 +599,19 @@ var Resource = (
|
|
|
624
599
|
};
|
|
625
600
|
Resource2.prototype.merge = function(other) {
|
|
626
601
|
var _this = this;
|
|
627
|
-
var
|
|
602
|
+
var _a;
|
|
628
603
|
if (!other)
|
|
629
604
|
return this;
|
|
630
|
-
var mergedSyncAttributes = __assign(__assign({}, this._syncAttributes), (
|
|
605
|
+
var mergedSyncAttributes = __assign(__assign({}, this._syncAttributes), (_a = other._syncAttributes) !== null && _a !== void 0 ? _a : other.attributes);
|
|
631
606
|
if (!this._asyncAttributesPromise && !other._asyncAttributesPromise) {
|
|
632
607
|
return new Resource2(mergedSyncAttributes);
|
|
633
608
|
}
|
|
634
609
|
var mergedAttributesPromise = Promise.all([
|
|
635
610
|
this._asyncAttributesPromise,
|
|
636
611
|
other._asyncAttributesPromise
|
|
637
|
-
]).then(function(
|
|
612
|
+
]).then(function(_a2) {
|
|
638
613
|
var _b;
|
|
639
|
-
var _c = __read(
|
|
614
|
+
var _c = __read(_a2, 2), thisAsyncAttributes = _c[0], otherAsyncAttributes = _c[1];
|
|
640
615
|
return __assign(__assign(__assign(__assign({}, _this._syncAttributes), thisAsyncAttributes), (_b = other._syncAttributes) !== null && _b !== void 0 ? _b : other.attributes), otherAsyncAttributes);
|
|
641
616
|
});
|
|
642
617
|
return new Resource2(mergedSyncAttributes, mergedAttributesPromise);
|
|
@@ -1620,6 +1595,127 @@ function createStreamObjectWrapper(aiModule) {
|
|
|
1620
1595
|
return result;
|
|
1621
1596
|
};
|
|
1622
1597
|
}
|
|
1598
|
+
function wrapMastraAgent(agent) {
|
|
1599
|
+
const originalGenerate = agent.generate.bind(agent);
|
|
1600
|
+
const agentName = agent.name || "MastraAgent";
|
|
1601
|
+
agent.generate = async function(...args) {
|
|
1602
|
+
const ctx = sessionStorage.getStore() || fallbackSession;
|
|
1603
|
+
if (!ctx || !initialized) {
|
|
1604
|
+
return originalGenerate(...args);
|
|
1605
|
+
}
|
|
1606
|
+
let promptCtx = null;
|
|
1607
|
+
try {
|
|
1608
|
+
const { getPromptContext } = await import("./prompts-VAN5E3L4.mjs");
|
|
1609
|
+
promptCtx = getPromptContext();
|
|
1610
|
+
} catch {
|
|
1611
|
+
}
|
|
1612
|
+
const traceId = generateHexId(32);
|
|
1613
|
+
const spanId = generateHexId(16);
|
|
1614
|
+
const startTime = Date.now();
|
|
1615
|
+
const messages = args[0] || [];
|
|
1616
|
+
try {
|
|
1617
|
+
const result = await originalGenerate(...args);
|
|
1618
|
+
const endTime = Date.now();
|
|
1619
|
+
const model = result?.model?.modelId || "unknown";
|
|
1620
|
+
const toolCalls = [];
|
|
1621
|
+
if (result?.steps?.length) {
|
|
1622
|
+
for (const step of result.steps) {
|
|
1623
|
+
if (step.toolCalls?.length) {
|
|
1624
|
+
for (let i = 0; i < step.toolCalls.length; i++) {
|
|
1625
|
+
const tc = step.toolCalls[i];
|
|
1626
|
+
const tr = step.toolResults?.[i];
|
|
1627
|
+
toolCalls.push({
|
|
1628
|
+
name: tc.toolName,
|
|
1629
|
+
arguments: tc.args,
|
|
1630
|
+
result: tr?.result
|
|
1631
|
+
});
|
|
1632
|
+
}
|
|
1633
|
+
}
|
|
1634
|
+
}
|
|
1635
|
+
}
|
|
1636
|
+
const attributes = {
|
|
1637
|
+
"gen_ai.system": "Mastra",
|
|
1638
|
+
"gen_ai.request.model": model,
|
|
1639
|
+
"gen_ai.response.model": model,
|
|
1640
|
+
"fallom.source": "mastra-agent",
|
|
1641
|
+
"llm.request.type": "chat"
|
|
1642
|
+
};
|
|
1643
|
+
if (Array.isArray(messages)) {
|
|
1644
|
+
messages.forEach((msg, i) => {
|
|
1645
|
+
attributes[`gen_ai.prompt.${i}.role`] = msg.role || "user";
|
|
1646
|
+
attributes[`gen_ai.prompt.${i}.content`] = typeof msg.content === "string" ? msg.content : JSON.stringify(msg.content);
|
|
1647
|
+
});
|
|
1648
|
+
}
|
|
1649
|
+
if (result?.text) {
|
|
1650
|
+
attributes["gen_ai.completion.0.role"] = "assistant";
|
|
1651
|
+
attributes["gen_ai.completion.0.content"] = result.text;
|
|
1652
|
+
attributes["gen_ai.completion.0.finish_reason"] = "stop";
|
|
1653
|
+
}
|
|
1654
|
+
if (toolCalls.length > 0) {
|
|
1655
|
+
attributes["fallom.tool_calls"] = JSON.stringify(toolCalls);
|
|
1656
|
+
toolCalls.forEach((tc, i) => {
|
|
1657
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.name`] = tc.name;
|
|
1658
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.type`] = "function";
|
|
1659
|
+
attributes[`gen_ai.completion.0.tool_calls.${i}.arguments`] = JSON.stringify(tc.arguments);
|
|
1660
|
+
});
|
|
1661
|
+
}
|
|
1662
|
+
if (result?.usage) {
|
|
1663
|
+
attributes["gen_ai.usage.prompt_tokens"] = result.usage.promptTokens;
|
|
1664
|
+
attributes["gen_ai.usage.completion_tokens"] = result.usage.completionTokens;
|
|
1665
|
+
attributes["llm.usage.total_tokens"] = result.usage.totalTokens;
|
|
1666
|
+
}
|
|
1667
|
+
const traceData = {
|
|
1668
|
+
config_key: ctx.configKey,
|
|
1669
|
+
session_id: ctx.sessionId,
|
|
1670
|
+
customer_id: ctx.customerId,
|
|
1671
|
+
trace_id: traceId,
|
|
1672
|
+
span_id: spanId,
|
|
1673
|
+
name: `mastra.${agentName}.generate`,
|
|
1674
|
+
kind: "client",
|
|
1675
|
+
model,
|
|
1676
|
+
start_time: new Date(startTime).toISOString(),
|
|
1677
|
+
end_time: new Date(endTime).toISOString(),
|
|
1678
|
+
duration_ms: endTime - startTime,
|
|
1679
|
+
status: "OK",
|
|
1680
|
+
prompt_tokens: result?.usage?.promptTokens,
|
|
1681
|
+
completion_tokens: result?.usage?.completionTokens,
|
|
1682
|
+
total_tokens: result?.usage?.totalTokens,
|
|
1683
|
+
attributes,
|
|
1684
|
+
prompt_key: promptCtx?.promptKey,
|
|
1685
|
+
prompt_version: promptCtx?.promptVersion,
|
|
1686
|
+
prompt_ab_test_key: promptCtx?.abTestKey,
|
|
1687
|
+
prompt_variant_index: promptCtx?.variantIndex
|
|
1688
|
+
};
|
|
1689
|
+
sendTrace(traceData).catch(() => {
|
|
1690
|
+
});
|
|
1691
|
+
return result;
|
|
1692
|
+
} catch (error) {
|
|
1693
|
+
const endTime = Date.now();
|
|
1694
|
+
const traceData = {
|
|
1695
|
+
config_key: ctx.configKey,
|
|
1696
|
+
session_id: ctx.sessionId,
|
|
1697
|
+
customer_id: ctx.customerId,
|
|
1698
|
+
trace_id: traceId,
|
|
1699
|
+
span_id: spanId,
|
|
1700
|
+
name: `mastra.${agentName}.generate`,
|
|
1701
|
+
kind: "client",
|
|
1702
|
+
start_time: new Date(startTime).toISOString(),
|
|
1703
|
+
end_time: new Date(endTime).toISOString(),
|
|
1704
|
+
duration_ms: endTime - startTime,
|
|
1705
|
+
status: "ERROR",
|
|
1706
|
+
error_message: error instanceof Error ? error.message : String(error),
|
|
1707
|
+
prompt_key: promptCtx?.promptKey,
|
|
1708
|
+
prompt_version: promptCtx?.promptVersion,
|
|
1709
|
+
prompt_ab_test_key: promptCtx?.abTestKey,
|
|
1710
|
+
prompt_variant_index: promptCtx?.variantIndex
|
|
1711
|
+
};
|
|
1712
|
+
sendTrace(traceData).catch(() => {
|
|
1713
|
+
});
|
|
1714
|
+
throw error;
|
|
1715
|
+
}
|
|
1716
|
+
};
|
|
1717
|
+
return agent;
|
|
1718
|
+
}
|
|
1623
1719
|
|
|
1624
1720
|
// src/models.ts
|
|
1625
1721
|
var models_exports = {};
|
|
@@ -1885,6 +1981,241 @@ async function init4(options = {}) {
|
|
|
1885
1981
|
});
|
|
1886
1982
|
}
|
|
1887
1983
|
|
|
1984
|
+
// src/mastra.ts
|
|
1985
|
+
import { ExportResultCode } from "@opentelemetry/core";
|
|
1986
|
+
var promptContext = {};
|
|
1987
|
+
function setMastraPrompt(promptKey, version) {
|
|
1988
|
+
promptContext = {
|
|
1989
|
+
promptKey,
|
|
1990
|
+
promptVersion: version,
|
|
1991
|
+
promptAbTestKey: void 0,
|
|
1992
|
+
promptVariantIndex: void 0
|
|
1993
|
+
};
|
|
1994
|
+
}
|
|
1995
|
+
function setMastraPromptAB(abTestKey, variantIndex) {
|
|
1996
|
+
promptContext = {
|
|
1997
|
+
promptKey: void 0,
|
|
1998
|
+
promptVersion: void 0,
|
|
1999
|
+
promptAbTestKey: abTestKey,
|
|
2000
|
+
promptVariantIndex: variantIndex
|
|
2001
|
+
};
|
|
2002
|
+
}
|
|
2003
|
+
function clearMastraPrompt() {
|
|
2004
|
+
promptContext = {};
|
|
2005
|
+
}
|
|
2006
|
+
var FallomExporter = class {
|
|
2007
|
+
constructor(options = {}) {
|
|
2008
|
+
this.pendingExports = [];
|
|
2009
|
+
this.apiKey = options.apiKey ?? process.env.FALLOM_API_KEY ?? "";
|
|
2010
|
+
this.baseUrl = options.baseUrl ?? "https://traces.fallom.com";
|
|
2011
|
+
this.debug = options.debug ?? false;
|
|
2012
|
+
console.log("[FallomExporter] Constructor called, debug:", this.debug);
|
|
2013
|
+
console.log("[FallomExporter] API key present:", !!this.apiKey);
|
|
2014
|
+
console.log("[FallomExporter] Base URL:", this.baseUrl);
|
|
2015
|
+
if (!this.apiKey) {
|
|
2016
|
+
console.warn(
|
|
2017
|
+
"[FallomExporter] No API key provided. Set FALLOM_API_KEY env var or pass apiKey option."
|
|
2018
|
+
);
|
|
2019
|
+
}
|
|
2020
|
+
}
|
|
2021
|
+
log(...args) {
|
|
2022
|
+
if (this.debug) {
|
|
2023
|
+
console.log("[FallomExporter]", ...args);
|
|
2024
|
+
}
|
|
2025
|
+
}
|
|
2026
|
+
/**
|
|
2027
|
+
* Export spans to Fallom.
|
|
2028
|
+
*/
|
|
2029
|
+
export(spans, resultCallback) {
|
|
2030
|
+
if (spans.length === 0) {
|
|
2031
|
+
resultCallback({ code: ExportResultCode.SUCCESS });
|
|
2032
|
+
return;
|
|
2033
|
+
}
|
|
2034
|
+
this.log(`Exporting ${spans.length} spans...`);
|
|
2035
|
+
if (this.debug) {
|
|
2036
|
+
for (const span2 of spans) {
|
|
2037
|
+
this.log(` - ${span2.name}`, {
|
|
2038
|
+
attributes: Object.fromEntries(
|
|
2039
|
+
Object.entries(span2.attributes).filter(
|
|
2040
|
+
([k]) => k.startsWith("gen_ai") || k.startsWith("llm")
|
|
2041
|
+
)
|
|
2042
|
+
)
|
|
2043
|
+
});
|
|
2044
|
+
}
|
|
2045
|
+
}
|
|
2046
|
+
const exportPromise = this.sendSpans(spans).then(() => {
|
|
2047
|
+
this.log("Export successful");
|
|
2048
|
+
resultCallback({ code: ExportResultCode.SUCCESS });
|
|
2049
|
+
}).catch((error) => {
|
|
2050
|
+
console.error("[FallomExporter] Export failed:", error);
|
|
2051
|
+
resultCallback({
|
|
2052
|
+
code: ExportResultCode.FAILED,
|
|
2053
|
+
error: error instanceof Error ? error : new Error(String(error))
|
|
2054
|
+
});
|
|
2055
|
+
});
|
|
2056
|
+
this.pendingExports.push(exportPromise);
|
|
2057
|
+
}
|
|
2058
|
+
/**
|
|
2059
|
+
* Shutdown the exporter, waiting for pending exports.
|
|
2060
|
+
*/
|
|
2061
|
+
async shutdown() {
|
|
2062
|
+
await Promise.all(this.pendingExports);
|
|
2063
|
+
this.pendingExports = [];
|
|
2064
|
+
}
|
|
2065
|
+
/**
|
|
2066
|
+
* Force flush pending exports.
|
|
2067
|
+
*/
|
|
2068
|
+
async forceFlush() {
|
|
2069
|
+
await Promise.all(this.pendingExports);
|
|
2070
|
+
}
|
|
2071
|
+
/**
|
|
2072
|
+
* Send spans to Fallom's OTLP endpoint.
|
|
2073
|
+
*/
|
|
2074
|
+
async sendSpans(spans) {
|
|
2075
|
+
const session = getSession();
|
|
2076
|
+
const resourceSpans = this.spansToOtlpJson(spans);
|
|
2077
|
+
const headers = {
|
|
2078
|
+
"Content-Type": "application/json",
|
|
2079
|
+
Authorization: `Bearer ${this.apiKey}`
|
|
2080
|
+
};
|
|
2081
|
+
if (session?.configKey) {
|
|
2082
|
+
headers["X-Fallom-Config-Key"] = session.configKey;
|
|
2083
|
+
}
|
|
2084
|
+
if (session?.sessionId) {
|
|
2085
|
+
headers["X-Fallom-Session-Id"] = session.sessionId;
|
|
2086
|
+
}
|
|
2087
|
+
if (session?.customerId) {
|
|
2088
|
+
headers["X-Fallom-Customer-Id"] = session.customerId;
|
|
2089
|
+
}
|
|
2090
|
+
if (promptContext.promptKey) {
|
|
2091
|
+
headers["X-Fallom-Prompt-Key"] = promptContext.promptKey;
|
|
2092
|
+
}
|
|
2093
|
+
if (promptContext.promptVersion !== void 0) {
|
|
2094
|
+
headers["X-Fallom-Prompt-Version"] = String(promptContext.promptVersion);
|
|
2095
|
+
}
|
|
2096
|
+
if (promptContext.promptAbTestKey) {
|
|
2097
|
+
headers["X-Fallom-Prompt-AB-Test"] = promptContext.promptAbTestKey;
|
|
2098
|
+
}
|
|
2099
|
+
if (promptContext.promptVariantIndex !== void 0) {
|
|
2100
|
+
headers["X-Fallom-Prompt-Variant"] = String(
|
|
2101
|
+
promptContext.promptVariantIndex
|
|
2102
|
+
);
|
|
2103
|
+
}
|
|
2104
|
+
const endpoint = `${this.baseUrl}/v1/traces`;
|
|
2105
|
+
this.log("Sending to", endpoint);
|
|
2106
|
+
this.log("Headers:", {
|
|
2107
|
+
...headers,
|
|
2108
|
+
Authorization: "Bearer ***"
|
|
2109
|
+
});
|
|
2110
|
+
const response = await fetch(endpoint, {
|
|
2111
|
+
method: "POST",
|
|
2112
|
+
headers,
|
|
2113
|
+
body: JSON.stringify({ resourceSpans })
|
|
2114
|
+
});
|
|
2115
|
+
if (!response.ok) {
|
|
2116
|
+
const text = await response.text();
|
|
2117
|
+
throw new Error(`Failed to export: ${response.status} ${text}`);
|
|
2118
|
+
}
|
|
2119
|
+
}
|
|
2120
|
+
/**
|
|
2121
|
+
* Convert OpenTelemetry spans to OTLP JSON format.
|
|
2122
|
+
*/
|
|
2123
|
+
spansToOtlpJson(spans) {
|
|
2124
|
+
const resourceMap = /* @__PURE__ */ new Map();
|
|
2125
|
+
for (const span2 of spans) {
|
|
2126
|
+
const resourceKey = JSON.stringify(span2.resource.attributes);
|
|
2127
|
+
if (!resourceMap.has(resourceKey)) {
|
|
2128
|
+
resourceMap.set(resourceKey, []);
|
|
2129
|
+
}
|
|
2130
|
+
resourceMap.get(resourceKey).push(span2);
|
|
2131
|
+
}
|
|
2132
|
+
const resourceSpans = [];
|
|
2133
|
+
for (const [_resourceKey, resourceSpanList] of resourceMap) {
|
|
2134
|
+
const firstSpan = resourceSpanList[0];
|
|
2135
|
+
resourceSpans.push({
|
|
2136
|
+
resource: {
|
|
2137
|
+
attributes: this.attributesToOtlp(firstSpan.resource.attributes)
|
|
2138
|
+
},
|
|
2139
|
+
scopeSpans: [
|
|
2140
|
+
{
|
|
2141
|
+
scope: {
|
|
2142
|
+
name: firstSpan.instrumentationLibrary.name,
|
|
2143
|
+
version: firstSpan.instrumentationLibrary.version
|
|
2144
|
+
},
|
|
2145
|
+
spans: resourceSpanList.map((span2) => this.spanToOtlp(span2))
|
|
2146
|
+
}
|
|
2147
|
+
]
|
|
2148
|
+
});
|
|
2149
|
+
}
|
|
2150
|
+
return resourceSpans;
|
|
2151
|
+
}
|
|
2152
|
+
/**
|
|
2153
|
+
* Convert a single span to OTLP format.
|
|
2154
|
+
*/
|
|
2155
|
+
spanToOtlp(span2) {
|
|
2156
|
+
return {
|
|
2157
|
+
traceId: span2.spanContext().traceId,
|
|
2158
|
+
spanId: span2.spanContext().spanId,
|
|
2159
|
+
parentSpanId: span2.parentSpanId,
|
|
2160
|
+
name: span2.name,
|
|
2161
|
+
kind: span2.kind,
|
|
2162
|
+
startTimeUnixNano: this.hrTimeToNanos(span2.startTime),
|
|
2163
|
+
endTimeUnixNano: this.hrTimeToNanos(span2.endTime),
|
|
2164
|
+
attributes: this.attributesToOtlp(span2.attributes),
|
|
2165
|
+
status: {
|
|
2166
|
+
code: span2.status.code,
|
|
2167
|
+
message: span2.status.message
|
|
2168
|
+
},
|
|
2169
|
+
events: span2.events.map((event) => ({
|
|
2170
|
+
timeUnixNano: this.hrTimeToNanos(event.time),
|
|
2171
|
+
name: event.name,
|
|
2172
|
+
attributes: this.attributesToOtlp(event.attributes || {})
|
|
2173
|
+
}))
|
|
2174
|
+
};
|
|
2175
|
+
}
|
|
2176
|
+
/**
|
|
2177
|
+
* Convert attributes to OTLP format.
|
|
2178
|
+
*/
|
|
2179
|
+
attributesToOtlp(attrs) {
|
|
2180
|
+
return Object.entries(attrs).map(([key, value]) => ({
|
|
2181
|
+
key,
|
|
2182
|
+
value: this.valueToOtlp(value)
|
|
2183
|
+
}));
|
|
2184
|
+
}
|
|
2185
|
+
/**
|
|
2186
|
+
* Convert a value to OTLP AnyValue format.
|
|
2187
|
+
*/
|
|
2188
|
+
valueToOtlp(value) {
|
|
2189
|
+
if (typeof value === "string") {
|
|
2190
|
+
return { stringValue: value };
|
|
2191
|
+
}
|
|
2192
|
+
if (typeof value === "number") {
|
|
2193
|
+
if (Number.isInteger(value)) {
|
|
2194
|
+
return { intValue: value };
|
|
2195
|
+
}
|
|
2196
|
+
return { doubleValue: value };
|
|
2197
|
+
}
|
|
2198
|
+
if (typeof value === "boolean") {
|
|
2199
|
+
return { boolValue: value };
|
|
2200
|
+
}
|
|
2201
|
+
if (Array.isArray(value)) {
|
|
2202
|
+
return {
|
|
2203
|
+
arrayValue: {
|
|
2204
|
+
values: value.map((v) => this.valueToOtlp(v))
|
|
2205
|
+
}
|
|
2206
|
+
};
|
|
2207
|
+
}
|
|
2208
|
+
return { stringValue: String(value) };
|
|
2209
|
+
}
|
|
2210
|
+
/**
|
|
2211
|
+
* Convert HrTime to nanoseconds string.
|
|
2212
|
+
*/
|
|
2213
|
+
hrTimeToNanos(hrTime) {
|
|
2214
|
+
const [seconds, nanos] = hrTime;
|
|
2215
|
+
return String(BigInt(seconds) * BigInt(1e9) + BigInt(nanos));
|
|
2216
|
+
}
|
|
2217
|
+
};
|
|
2218
|
+
|
|
1888
2219
|
// src/index.ts
|
|
1889
2220
|
var index_default = {
|
|
1890
2221
|
init: init4,
|
|
@@ -1893,9 +2224,13 @@ var index_default = {
|
|
|
1893
2224
|
prompts: prompts_exports
|
|
1894
2225
|
};
|
|
1895
2226
|
export {
|
|
2227
|
+
FallomExporter,
|
|
2228
|
+
clearMastraPrompt,
|
|
1896
2229
|
index_default as default,
|
|
1897
2230
|
init4 as init,
|
|
1898
2231
|
models_exports as models,
|
|
1899
2232
|
prompts_exports as prompts,
|
|
2233
|
+
setMastraPrompt,
|
|
2234
|
+
setMastraPromptAB,
|
|
1900
2235
|
trace_exports as trace
|
|
1901
2236
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fallom/trace",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.11",
|
|
4
4
|
"description": "Model A/B testing and tracing for LLM applications. Zero latency, production-ready.",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"module": "./dist/index.mjs",
|
|
@@ -44,7 +44,9 @@
|
|
|
44
44
|
},
|
|
45
45
|
"dependencies": {
|
|
46
46
|
"@opentelemetry/api": "^1.7.0",
|
|
47
|
+
"@opentelemetry/core": "^1.19.0",
|
|
47
48
|
"@opentelemetry/sdk-node": "^0.46.0",
|
|
49
|
+
"@opentelemetry/sdk-trace-base": "^1.19.0",
|
|
48
50
|
"@opentelemetry/sdk-trace-node": "^1.19.0",
|
|
49
51
|
"@opentelemetry/exporter-trace-otlp-http": "^0.46.0",
|
|
50
52
|
"@traceloop/instrumentation-openai": "^0.11.0",
|