@amaster.ai/pi-telemetry 0.1.2-beta.0 → 0.1.2-beta.10
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/README.md +24 -3
- package/dist/config.d.ts +2 -2
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +3 -2
- package/dist/config.js.map +1 -1
- package/dist/extension.d.ts.map +1 -1
- package/dist/extension.js +235 -48
- package/dist/extension.js.map +1 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -1
- package/dist/index.js.map +1 -1
- package/dist/langfuse.d.ts +0 -24
- package/dist/langfuse.d.ts.map +1 -1
- package/dist/langfuse.js +12 -295
- package/dist/langfuse.js.map +1 -1
- package/package.json +18 -2
package/dist/langfuse.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { createHash
|
|
1
|
+
import { createHash } from 'node:crypto';
|
|
2
2
|
import { Langfuse } from 'langfuse';
|
|
3
3
|
import { NoopRuntimeEventExporter, } from './index.js';
|
|
4
4
|
const DEFAULT_LANGFUSE_BASE_URL = 'https://cloud.langfuse.com';
|
|
@@ -53,7 +53,7 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
53
53
|
case 'chat_turn_started': {
|
|
54
54
|
const body = {
|
|
55
55
|
id: rootSpanId,
|
|
56
|
-
name: '
|
|
56
|
+
name: 'chat-turn',
|
|
57
57
|
startTime: event.createdAt,
|
|
58
58
|
input: event.details?.input,
|
|
59
59
|
level: 'DEFAULT',
|
|
@@ -78,14 +78,14 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
78
78
|
this.closeSdkSubagentBatchSpans(traceId, event);
|
|
79
79
|
trace.update({
|
|
80
80
|
sessionId: event.sessionId,
|
|
81
|
-
name: '
|
|
81
|
+
name: 'chat-turn',
|
|
82
82
|
output,
|
|
83
83
|
metadata: lifecycleMetadata(event),
|
|
84
84
|
});
|
|
85
85
|
const span = this.spans.get(rootKey) ??
|
|
86
86
|
trace.span({
|
|
87
87
|
id: rootSpanId,
|
|
88
|
-
name: '
|
|
88
|
+
name: 'chat-turn',
|
|
89
89
|
startTime: event.createdAt,
|
|
90
90
|
metadata: lifecycleMetadata(event),
|
|
91
91
|
});
|
|
@@ -96,7 +96,6 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
96
96
|
...(event.error ? { statusMessage: event.error } : {}),
|
|
97
97
|
metadata: lifecycleMetadata(event),
|
|
98
98
|
});
|
|
99
|
-
this.spans.delete(rootKey);
|
|
100
99
|
break;
|
|
101
100
|
}
|
|
102
101
|
case 'chat_turn_steered':
|
|
@@ -119,7 +118,7 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
119
118
|
case 'subagent_spawned':
|
|
120
119
|
case 'subagent_started': {
|
|
121
120
|
const key = subagentSpanKey(event);
|
|
122
|
-
|
|
121
|
+
this.ensureSdkRootSpan(trace, rootKey, event);
|
|
123
122
|
const body = {
|
|
124
123
|
id: langfuseSpanId(traceId, key),
|
|
125
124
|
name: 'subagent',
|
|
@@ -146,7 +145,7 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
146
145
|
case 'subagent_cancelled': {
|
|
147
146
|
const key = subagentSpanKey(event);
|
|
148
147
|
const output = event.details?.output ?? (event.error ? { error: event.error } : undefined);
|
|
149
|
-
|
|
148
|
+
this.ensureSdkRootSpan(trace, rootKey, event);
|
|
150
149
|
const span = this.spans.get(key) ??
|
|
151
150
|
this.getSdkSubagentParent(trace, rootKey, event).span({
|
|
152
151
|
id: langfuseSpanId(traceId, key),
|
|
@@ -161,7 +160,6 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
161
160
|
...(event.error ? { statusMessage: event.error } : {}),
|
|
162
161
|
metadata: lifecycleMetadata(event),
|
|
163
162
|
});
|
|
164
|
-
this.spans.delete(key);
|
|
165
163
|
break;
|
|
166
164
|
}
|
|
167
165
|
default:
|
|
@@ -280,7 +278,7 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
280
278
|
const trace = this.client.trace({
|
|
281
279
|
id: langfuseTraceId(traceId),
|
|
282
280
|
sessionId: event.sessionId,
|
|
283
|
-
name: '
|
|
281
|
+
name: 'chat-turn',
|
|
284
282
|
timestamp: event.createdAt,
|
|
285
283
|
input: !isToolEvent(event) && !isLlmGenerationEvent(event) ? event.details?.input : undefined,
|
|
286
284
|
metadata: isToolEvent(event)
|
|
@@ -336,7 +334,6 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
336
334
|
...(event.error ? { statusMessage: event.error } : {}),
|
|
337
335
|
metadata: lifecycleMetadata(event),
|
|
338
336
|
});
|
|
339
|
-
this.spans.delete(key);
|
|
340
337
|
}
|
|
341
338
|
}
|
|
342
339
|
ensureSdkRootSpan(trace, rootKey, event) {
|
|
@@ -347,7 +344,7 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
347
344
|
const traceId = requireTraceId(event.traceId);
|
|
348
345
|
const span = trace.span({
|
|
349
346
|
id: langfuseSpanId(traceId, rootKey),
|
|
350
|
-
name: '
|
|
347
|
+
name: 'chat-turn',
|
|
351
348
|
startTime: event.createdAt,
|
|
352
349
|
metadata: isToolEvent(event)
|
|
353
350
|
? toolMetadata(event)
|
|
@@ -359,97 +356,6 @@ export class LangfuseSdkRuntimeEventExporter {
|
|
|
359
356
|
return span;
|
|
360
357
|
}
|
|
361
358
|
}
|
|
362
|
-
export class LangfuseHttpRuntimeEventExporter {
|
|
363
|
-
config;
|
|
364
|
-
endpoint;
|
|
365
|
-
authHeader;
|
|
366
|
-
fetchImpl;
|
|
367
|
-
queue = [];
|
|
368
|
-
flushTimer;
|
|
369
|
-
flushing;
|
|
370
|
-
constructor(config, fetchImpl) {
|
|
371
|
-
this.config = config;
|
|
372
|
-
this.endpoint = `${config.baseUrl.replace(/\/+$/, '')}/api/public/ingestion`;
|
|
373
|
-
this.authHeader = `Basic ${Buffer.from(`${config.publicKey}:${config.secretKey}`).toString('base64')}`;
|
|
374
|
-
this.fetchImpl =
|
|
375
|
-
fetchImpl ??
|
|
376
|
-
(async (input, init) => {
|
|
377
|
-
const response = await fetch(input, init);
|
|
378
|
-
return {
|
|
379
|
-
ok: response.ok,
|
|
380
|
-
status: response.status,
|
|
381
|
-
text: () => response.text(),
|
|
382
|
-
};
|
|
383
|
-
});
|
|
384
|
-
}
|
|
385
|
-
async publish(event) {
|
|
386
|
-
const redactedEvent = applyTelemetryRedaction(this.config, event);
|
|
387
|
-
if (!redactedEvent) {
|
|
388
|
-
return;
|
|
389
|
-
}
|
|
390
|
-
const mapped = mapRuntimeEventToLangfuse(redactedEvent);
|
|
391
|
-
if (mapped.length === 0) {
|
|
392
|
-
return;
|
|
393
|
-
}
|
|
394
|
-
this.queue.push(...mapped);
|
|
395
|
-
if (this.queue.length >= this.config.flushAt) {
|
|
396
|
-
await this.flush();
|
|
397
|
-
return;
|
|
398
|
-
}
|
|
399
|
-
this.scheduleFlush();
|
|
400
|
-
}
|
|
401
|
-
async flush() {
|
|
402
|
-
if (this.flushing) {
|
|
403
|
-
await this.flushing;
|
|
404
|
-
return;
|
|
405
|
-
}
|
|
406
|
-
if (this.flushTimer) {
|
|
407
|
-
clearTimeout(this.flushTimer);
|
|
408
|
-
this.flushTimer = undefined;
|
|
409
|
-
}
|
|
410
|
-
const batch = this.queue.splice(0, this.queue.length);
|
|
411
|
-
if (batch.length === 0) {
|
|
412
|
-
return;
|
|
413
|
-
}
|
|
414
|
-
this.flushing = this.sendBatch(batch)
|
|
415
|
-
.catch((error) => {
|
|
416
|
-
this.queue.unshift(...batch);
|
|
417
|
-
throw error;
|
|
418
|
-
})
|
|
419
|
-
.finally(() => {
|
|
420
|
-
this.flushing = undefined;
|
|
421
|
-
});
|
|
422
|
-
await this.flushing;
|
|
423
|
-
}
|
|
424
|
-
async close() {
|
|
425
|
-
await this.flush();
|
|
426
|
-
}
|
|
427
|
-
scheduleFlush() {
|
|
428
|
-
if (this.flushTimer) {
|
|
429
|
-
return;
|
|
430
|
-
}
|
|
431
|
-
this.flushTimer = setTimeout(() => {
|
|
432
|
-
this.flushTimer = undefined;
|
|
433
|
-
void this.flush().catch(() => undefined);
|
|
434
|
-
}, this.config.flushIntervalMs);
|
|
435
|
-
this.flushTimer.unref();
|
|
436
|
-
}
|
|
437
|
-
async sendBatch(batch) {
|
|
438
|
-
const response = await this.fetchImpl(this.endpoint, {
|
|
439
|
-
method: 'POST',
|
|
440
|
-
headers: {
|
|
441
|
-
authorization: this.authHeader,
|
|
442
|
-
'content-type': 'application/json',
|
|
443
|
-
'x-langfuse-ingestion-version': '4',
|
|
444
|
-
},
|
|
445
|
-
body: JSON.stringify({ batch }),
|
|
446
|
-
});
|
|
447
|
-
if (!response.ok) {
|
|
448
|
-
const text = await response.text().catch(() => '');
|
|
449
|
-
throw new Error(`Langfuse ingestion failed with ${response.status}${text ? `: ${text}` : ''}`);
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
}
|
|
453
359
|
export class OtelRuntimeEventExporter {
|
|
454
360
|
config;
|
|
455
361
|
endpoint;
|
|
@@ -545,31 +451,22 @@ export function createRuntimeEventExporterFromEnv(env) {
|
|
|
545
451
|
if (!config.enabled) {
|
|
546
452
|
return new NoopRuntimeEventExporter();
|
|
547
453
|
}
|
|
548
|
-
|
|
549
|
-
return new LangfuseSdkRuntimeEventExporter(config);
|
|
550
|
-
}
|
|
551
|
-
return new LangfuseHttpRuntimeEventExporter(config);
|
|
454
|
+
return new LangfuseSdkRuntimeEventExporter(config);
|
|
552
455
|
}
|
|
553
456
|
export function createLangfuseExporter(telemetryConfig) {
|
|
554
457
|
const config = resolveLangfuseExporterConfig(telemetryConfig);
|
|
555
458
|
if (!config.enabled) {
|
|
556
459
|
return new NoopRuntimeEventExporter();
|
|
557
460
|
}
|
|
558
|
-
|
|
559
|
-
return new LangfuseSdkRuntimeEventExporter(config);
|
|
560
|
-
}
|
|
561
|
-
return new LangfuseHttpRuntimeEventExporter(config);
|
|
461
|
+
return new LangfuseSdkRuntimeEventExporter(config);
|
|
562
462
|
}
|
|
563
463
|
export function resolveLangfuseExporterConfig(telemetryConfig) {
|
|
564
464
|
const lf = telemetryConfig.langfuse;
|
|
565
465
|
const publicKey = lf?.publicKey ?? '';
|
|
566
466
|
const secretKey = lf?.secretKey ?? '';
|
|
567
467
|
const credentialsPresent = Boolean(publicKey && secretKey);
|
|
568
|
-
const requestedTransport = lf?.transport;
|
|
569
|
-
const transport = requestedTransport ?? (credentialsPresent ? 'sdk' : 'ingestion');
|
|
570
468
|
return {
|
|
571
469
|
enabled: Boolean(lf?.enabled && credentialsPresent),
|
|
572
|
-
transport,
|
|
573
470
|
publicKey,
|
|
574
471
|
secretKey,
|
|
575
472
|
baseUrl: lf?.baseUrl ?? DEFAULT_LANGFUSE_BASE_URL,
|
|
@@ -585,13 +482,10 @@ export function resolveLangfuseConfig(env) {
|
|
|
585
482
|
const publicKey = trim(env.LANGFUSE_PUBLIC_KEY);
|
|
586
483
|
const secretKey = trim(env.LANGFUSE_SECRET_KEY);
|
|
587
484
|
const baseUrl = trim(env.LANGFUSE_BASE_URL) ?? DEFAULT_LANGFUSE_BASE_URL;
|
|
588
|
-
const requestedTransport = parseLangfuseTransport(env.LANGFUSE_TRANSPORT);
|
|
589
|
-
const transport = requestedTransport ?? (publicKey && secretKey ? 'sdk' : 'ingestion');
|
|
590
485
|
const credentialsPresent = Boolean(publicKey && secretKey);
|
|
591
486
|
const serviceVersion = trim(env.TELEMETRY_SERVICE_VERSION);
|
|
592
487
|
return {
|
|
593
488
|
enabled: Boolean(enabled && credentialsPresent),
|
|
594
|
-
transport,
|
|
595
489
|
publicKey: publicKey ?? '',
|
|
596
490
|
secretKey: secretKey ?? '',
|
|
597
491
|
baseUrl,
|
|
@@ -602,171 +496,6 @@ export function resolveLangfuseConfig(env) {
|
|
|
602
496
|
includePayloads: parseBooleanWithDefault(env.TELEMETRY_INCLUDE_PAYLOADS ?? env.LANGFUSE_INCLUDE_PAYLOADS, true),
|
|
603
497
|
};
|
|
604
498
|
}
|
|
605
|
-
export function mapRuntimeEventToLangfuse(event) {
|
|
606
|
-
if (!event.traceId) {
|
|
607
|
-
return [];
|
|
608
|
-
}
|
|
609
|
-
if (isLlmGenerationEvent(event)) {
|
|
610
|
-
return [mapLlmGenerationEventToLangfuse(event)];
|
|
611
|
-
}
|
|
612
|
-
if (isToolEvent(event)) {
|
|
613
|
-
return [mapToolEventToLangfuse(event)];
|
|
614
|
-
}
|
|
615
|
-
return mapLifecycleEventToLangfuse(event);
|
|
616
|
-
}
|
|
617
|
-
function mapLifecycleEventToLangfuse(event) {
|
|
618
|
-
const traceId = requireTraceId(event.traceId);
|
|
619
|
-
switch (event.type) {
|
|
620
|
-
case 'chat_turn_started':
|
|
621
|
-
return [
|
|
622
|
-
ingestionEvent('trace-create', event.createdAt, {
|
|
623
|
-
id: langfuseTraceId(traceId),
|
|
624
|
-
sessionId: event.sessionId,
|
|
625
|
-
name: 'copilot-chat-turn',
|
|
626
|
-
timestamp: event.createdAt,
|
|
627
|
-
input: event.details?.input,
|
|
628
|
-
metadata: lifecycleMetadata(event),
|
|
629
|
-
}),
|
|
630
|
-
];
|
|
631
|
-
case 'chat_turn_completed':
|
|
632
|
-
case 'chat_turn_failed': {
|
|
633
|
-
const output = event.details?.output ?? (event.error ? { error: event.error } : undefined);
|
|
634
|
-
return [
|
|
635
|
-
ingestionEvent('trace-update', event.createdAt, {
|
|
636
|
-
id: langfuseTraceId(traceId),
|
|
637
|
-
...(output !== undefined ? { output } : {}),
|
|
638
|
-
metadata: lifecycleMetadata(event),
|
|
639
|
-
}),
|
|
640
|
-
];
|
|
641
|
-
}
|
|
642
|
-
case 'chat_turn_steered':
|
|
643
|
-
case 'chat_turn_steer_delivered':
|
|
644
|
-
case 'chat_turn_followup_queued':
|
|
645
|
-
case 'chat_turn_followup_delivered': {
|
|
646
|
-
const spanId = langfuseSpanId(traceId, chatInputSpanKey(event));
|
|
647
|
-
return [
|
|
648
|
-
ingestionEvent('span-create', event.createdAt, {
|
|
649
|
-
id: spanId,
|
|
650
|
-
traceId: langfuseTraceId(traceId),
|
|
651
|
-
parentObservationId: langfuseSpanId(traceId, chatSpanKey(event)),
|
|
652
|
-
name: chatInputObservationName(event),
|
|
653
|
-
startTime: event.createdAt,
|
|
654
|
-
input: event.details?.input,
|
|
655
|
-
metadata: lifecycleMetadata(event),
|
|
656
|
-
}),
|
|
657
|
-
ingestionEvent('span-update', event.createdAt, {
|
|
658
|
-
id: spanId,
|
|
659
|
-
traceId: langfuseTraceId(traceId),
|
|
660
|
-
endTime: event.createdAt,
|
|
661
|
-
output: event.details?.output ?? chatInputLifecycleOutput(event),
|
|
662
|
-
metadata: lifecycleMetadata(event),
|
|
663
|
-
}),
|
|
664
|
-
];
|
|
665
|
-
}
|
|
666
|
-
case 'subagent_spawned':
|
|
667
|
-
case 'subagent_started': {
|
|
668
|
-
const batchKey = subagentBatchSpanKey(event);
|
|
669
|
-
return [
|
|
670
|
-
...(batchKey
|
|
671
|
-
? [
|
|
672
|
-
ingestionEvent('span-create', event.createdAt, {
|
|
673
|
-
id: langfuseSpanId(traceId, batchKey),
|
|
674
|
-
traceId: langfuseTraceId(traceId),
|
|
675
|
-
parentObservationId: langfuseSpanId(traceId, chatSpanKey(event)),
|
|
676
|
-
name: 'subagent fan-out',
|
|
677
|
-
startTime: event.createdAt,
|
|
678
|
-
input: event.details?.input,
|
|
679
|
-
metadata: lifecycleMetadata(event),
|
|
680
|
-
}),
|
|
681
|
-
]
|
|
682
|
-
: []),
|
|
683
|
-
ingestionEvent('span-create', event.createdAt, {
|
|
684
|
-
id: langfuseSpanId(traceId, subagentSpanKey(event)),
|
|
685
|
-
traceId: langfuseTraceId(traceId),
|
|
686
|
-
parentObservationId: langfuseSpanId(traceId, batchKey ?? subagentSpawnToolSpanKey(event) ?? chatSpanKey(event)),
|
|
687
|
-
name: 'subagent',
|
|
688
|
-
startTime: event.createdAt,
|
|
689
|
-
metadata: lifecycleMetadata(event),
|
|
690
|
-
}),
|
|
691
|
-
];
|
|
692
|
-
}
|
|
693
|
-
case 'subagent_completed':
|
|
694
|
-
case 'subagent_failed':
|
|
695
|
-
case 'subagent_cancelled':
|
|
696
|
-
return [
|
|
697
|
-
ingestionEvent('span-update', event.createdAt, {
|
|
698
|
-
id: langfuseSpanId(traceId, subagentSpanKey(event)),
|
|
699
|
-
traceId: langfuseTraceId(traceId),
|
|
700
|
-
endTime: event.createdAt,
|
|
701
|
-
metadata: lifecycleMetadata(event),
|
|
702
|
-
...(event.error ? { output: { error: event.error } } : {}),
|
|
703
|
-
}),
|
|
704
|
-
];
|
|
705
|
-
default:
|
|
706
|
-
return assertNever(event.type);
|
|
707
|
-
}
|
|
708
|
-
}
|
|
709
|
-
function mapToolEventToLangfuse(event) {
|
|
710
|
-
const traceId = requireTraceId(event.traceId);
|
|
711
|
-
const spanId = langfuseSpanId(traceId, `tool:${event.sessionId}:${event.toolCallId}:${event.toolName}`);
|
|
712
|
-
const parentObservationId = langfuseParentObservationId(traceId, event);
|
|
713
|
-
if (event.status === 'started') {
|
|
714
|
-
return ingestionEvent('span-create', event.createdAt, {
|
|
715
|
-
id: spanId,
|
|
716
|
-
traceId: langfuseTraceId(traceId),
|
|
717
|
-
parentObservationId,
|
|
718
|
-
name: toolObservationName(event),
|
|
719
|
-
startTime: event.createdAt,
|
|
720
|
-
input: event.args ?? {},
|
|
721
|
-
metadata: toolMetadata(event),
|
|
722
|
-
});
|
|
723
|
-
}
|
|
724
|
-
return ingestionEvent('span-update', event.createdAt, {
|
|
725
|
-
id: spanId,
|
|
726
|
-
traceId: langfuseTraceId(traceId),
|
|
727
|
-
endTime: event.createdAt,
|
|
728
|
-
metadata: toolMetadata(event),
|
|
729
|
-
...(event.error ? { output: { error: event.error } } : { output: event.details ?? {} }),
|
|
730
|
-
});
|
|
731
|
-
}
|
|
732
|
-
function mapLlmGenerationEventToLangfuse(event) {
|
|
733
|
-
const traceId = requireTraceId(event.traceId);
|
|
734
|
-
const id = langfuseSpanId(traceId, llmGenerationKey(event));
|
|
735
|
-
const parentObservationId = langfuseParentObservationId(traceId, event);
|
|
736
|
-
if (event.status === 'started') {
|
|
737
|
-
return ingestionEvent('generation-create', event.createdAt, {
|
|
738
|
-
id,
|
|
739
|
-
traceId: langfuseTraceId(traceId),
|
|
740
|
-
parentObservationId,
|
|
741
|
-
name: llmGenerationObservationName(event),
|
|
742
|
-
startTime: event.createdAt,
|
|
743
|
-
model: event.model.model,
|
|
744
|
-
modelParameters: {
|
|
745
|
-
provider: event.model.provider,
|
|
746
|
-
...(event.model.thinkingLevel ? { thinkingLevel: event.model.thinkingLevel } : {}),
|
|
747
|
-
},
|
|
748
|
-
input: event.input,
|
|
749
|
-
metadata: llmGenerationMetadata(event),
|
|
750
|
-
});
|
|
751
|
-
}
|
|
752
|
-
return ingestionEvent('generation-update', event.createdAt, {
|
|
753
|
-
id,
|
|
754
|
-
traceId: langfuseTraceId(traceId),
|
|
755
|
-
endTime: event.createdAt,
|
|
756
|
-
output: event.output ?? (event.error ? { error: event.error } : undefined),
|
|
757
|
-
level: event.error ? 'ERROR' : 'DEFAULT',
|
|
758
|
-
...(event.error ? { statusMessage: event.error } : {}),
|
|
759
|
-
...(event.usage
|
|
760
|
-
? { usage: toLangfuseUsage(event.usage), usageDetails: toLangfuseUsageDetails(event.usage) }
|
|
761
|
-
: {}),
|
|
762
|
-
model: event.model.model,
|
|
763
|
-
modelParameters: {
|
|
764
|
-
provider: event.model.provider,
|
|
765
|
-
...(event.model.thinkingLevel ? { thinkingLevel: event.model.thinkingLevel } : {}),
|
|
766
|
-
},
|
|
767
|
-
metadata: llmGenerationMetadata(event),
|
|
768
|
-
});
|
|
769
|
-
}
|
|
770
499
|
function mapRuntimeEventToOtelSpans(event, pendingStarts) {
|
|
771
500
|
if (!event.traceId) {
|
|
772
501
|
return [];
|
|
@@ -787,7 +516,7 @@ function mapLifecycleEventToOtelSpans(event, pendingStarts) {
|
|
|
787
516
|
pendingStarts.set(rootKey, {
|
|
788
517
|
traceId: langfuseTraceId(traceId),
|
|
789
518
|
spanId: rootSpanId,
|
|
790
|
-
name: '
|
|
519
|
+
name: 'chat-turn',
|
|
791
520
|
startTime: event.createdAt,
|
|
792
521
|
attributes: {
|
|
793
522
|
...lifecycleMetadata(event),
|
|
@@ -802,7 +531,7 @@ function mapLifecycleEventToOtelSpans(event, pendingStarts) {
|
|
|
802
531
|
completeOtelSpan(pendingStarts, rootKey, {
|
|
803
532
|
traceId: langfuseTraceId(traceId),
|
|
804
533
|
spanId: rootSpanId,
|
|
805
|
-
name: '
|
|
534
|
+
name: 'chat-turn',
|
|
806
535
|
startTime: event.createdAt,
|
|
807
536
|
attributes: {
|
|
808
537
|
...lifecycleMetadata(event),
|
|
@@ -1282,14 +1011,6 @@ function flattenUsageAttributes(usage) {
|
|
|
1282
1011
|
...(usage.cost?.total !== undefined ? { 'usage.cost.total': usage.cost.total } : {}),
|
|
1283
1012
|
};
|
|
1284
1013
|
}
|
|
1285
|
-
function ingestionEvent(type, timestamp, body) {
|
|
1286
|
-
return {
|
|
1287
|
-
id: randomUUID(),
|
|
1288
|
-
timestamp,
|
|
1289
|
-
type,
|
|
1290
|
-
body,
|
|
1291
|
-
};
|
|
1292
|
-
}
|
|
1293
1014
|
function langfuseTraceId(traceId) {
|
|
1294
1015
|
return stableHex(`trace:${traceId}`, 32);
|
|
1295
1016
|
}
|
|
@@ -1343,10 +1064,6 @@ function parseBooleanWithDefault(value, fallback) {
|
|
|
1343
1064
|
}
|
|
1344
1065
|
return parseBoolean(value);
|
|
1345
1066
|
}
|
|
1346
|
-
function parseLangfuseTransport(value) {
|
|
1347
|
-
const normalized = value?.trim().toLowerCase();
|
|
1348
|
-
return normalized === 'sdk' || normalized === 'ingestion' ? normalized : undefined;
|
|
1349
|
-
}
|
|
1350
1067
|
function parsePositiveInteger(value, fallback) {
|
|
1351
1068
|
const parsed = Number(value);
|
|
1352
1069
|
return Number.isInteger(parsed) && parsed > 0 ? parsed : fallback;
|