@mastra/langfuse 0.0.0-add-libsql-changeset-20250910154739
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/CHANGELOG.md +181 -0
- package/LICENSE.md +15 -0
- package/README.md +49 -0
- package/dist/ai-tracing.d.ts +41 -0
- package/dist/ai-tracing.d.ts.map +1 -0
- package/dist/index.cjs +225 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.ts +8 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +223 -0
- package/dist/index.js.map +1 -0
- package/package.json +59 -0
package/CHANGELOG.md
ADDED
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
# @mastra/langfuse
|
|
2
|
+
|
|
3
|
+
## 0.0.0-add-libsql-changeset-20250910154739
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- "updated observability config" ([#7641](https://github.com/mastra-ai/mastra/pull/7641))
|
|
8
|
+
|
|
9
|
+
- Updated dependencies [[`b4379f7`](https://github.com/mastra-ai/mastra/commit/b4379f703fd74474f253420e8c3a684f2c4b2f8e), [`d34aaa1`](https://github.com/mastra-ai/mastra/commit/d34aaa1da5d3c5f991740f59e2fe6d28d3e2dd91), [`b2babfa`](https://github.com/mastra-ai/mastra/commit/b2babfa9e75b22f2759179e71d8473f6dc5421ed), [`d8c3ba5`](https://github.com/mastra-ai/mastra/commit/d8c3ba516f4173282d293f7e64769cfc8738d360), [`6424c7e`](https://github.com/mastra-ai/mastra/commit/6424c7ec38b6921d66212431db1e0958f441b2a7), [`db94750`](https://github.com/mastra-ai/mastra/commit/db94750a41fd29b43eb1f7ce8e97ba8b9978c91b), [`a66a371`](https://github.com/mastra-ai/mastra/commit/a66a3716b00553d7f01842be9deb34f720b10fab), [`69fc3cd`](https://github.com/mastra-ai/mastra/commit/69fc3cd0fd814901785bdcf49bf536ab1e7fd975)]:
|
|
10
|
+
- @mastra/core@0.0.0-add-libsql-changeset-20250910154739
|
|
11
|
+
|
|
12
|
+
## 0.0.6
|
|
13
|
+
|
|
14
|
+
### Patch Changes
|
|
15
|
+
|
|
16
|
+
- 209250e: Simplified langfuse exporter config
|
|
17
|
+
- 376913a: Update peerdeps
|
|
18
|
+
- Updated dependencies [8fbf79e]
|
|
19
|
+
- Updated dependencies [fd83526]
|
|
20
|
+
- Updated dependencies [d0b90ab]
|
|
21
|
+
- Updated dependencies [6f5eb7a]
|
|
22
|
+
- Updated dependencies [a01cf14]
|
|
23
|
+
- Updated dependencies [a9e50ee]
|
|
24
|
+
- Updated dependencies [5397eb4]
|
|
25
|
+
- Updated dependencies [c9f4e4a]
|
|
26
|
+
- Updated dependencies [0acbc80]
|
|
27
|
+
- @mastra/core@0.16.0
|
|
28
|
+
|
|
29
|
+
## 0.0.6-alpha.1
|
|
30
|
+
|
|
31
|
+
### Patch Changes
|
|
32
|
+
|
|
33
|
+
- 376913a: Update peerdeps
|
|
34
|
+
- Updated dependencies [8fbf79e]
|
|
35
|
+
- @mastra/core@0.16.0-alpha.1
|
|
36
|
+
|
|
37
|
+
## 0.0.6-alpha.0
|
|
38
|
+
|
|
39
|
+
### Patch Changes
|
|
40
|
+
|
|
41
|
+
- 209250e: Simplified langfuse exporter config
|
|
42
|
+
- Updated dependencies [fd83526]
|
|
43
|
+
- Updated dependencies [d0b90ab]
|
|
44
|
+
- Updated dependencies [6f5eb7a]
|
|
45
|
+
- Updated dependencies [a01cf14]
|
|
46
|
+
- Updated dependencies [a9e50ee]
|
|
47
|
+
- Updated dependencies [5397eb4]
|
|
48
|
+
- Updated dependencies [c9f4e4a]
|
|
49
|
+
- Updated dependencies [0acbc80]
|
|
50
|
+
- @mastra/core@0.16.0-alpha.0
|
|
51
|
+
|
|
52
|
+
## 0.0.5
|
|
53
|
+
|
|
54
|
+
### Patch Changes
|
|
55
|
+
|
|
56
|
+
- de3cbc6: Update the `package.json` file to include additional fields like `repository`, `homepage` or `files`.
|
|
57
|
+
- 979912c: "Updated langfuse exporter to handle Event spans"
|
|
58
|
+
- Updated dependencies [ab48c97]
|
|
59
|
+
- Updated dependencies [85ef90b]
|
|
60
|
+
- Updated dependencies [aedbbfa]
|
|
61
|
+
- Updated dependencies [ff89505]
|
|
62
|
+
- Updated dependencies [637f323]
|
|
63
|
+
- Updated dependencies [de3cbc6]
|
|
64
|
+
- Updated dependencies [c19bcf7]
|
|
65
|
+
- Updated dependencies [4474d04]
|
|
66
|
+
- Updated dependencies [183dc95]
|
|
67
|
+
- Updated dependencies [a1111e2]
|
|
68
|
+
- Updated dependencies [b42a961]
|
|
69
|
+
- Updated dependencies [61debef]
|
|
70
|
+
- Updated dependencies [9beaeff]
|
|
71
|
+
- Updated dependencies [29de0e1]
|
|
72
|
+
- Updated dependencies [f643c65]
|
|
73
|
+
- Updated dependencies [00c74e7]
|
|
74
|
+
- Updated dependencies [fef7375]
|
|
75
|
+
- Updated dependencies [e3d8fea]
|
|
76
|
+
- Updated dependencies [45e4d39]
|
|
77
|
+
- Updated dependencies [9eee594]
|
|
78
|
+
- Updated dependencies [7149d8d]
|
|
79
|
+
- Updated dependencies [822c2e8]
|
|
80
|
+
- Updated dependencies [979912c]
|
|
81
|
+
- Updated dependencies [7dcf4c0]
|
|
82
|
+
- Updated dependencies [4106a58]
|
|
83
|
+
- Updated dependencies [ad78bfc]
|
|
84
|
+
- Updated dependencies [0302f50]
|
|
85
|
+
- Updated dependencies [6ac697e]
|
|
86
|
+
- Updated dependencies [74db265]
|
|
87
|
+
- Updated dependencies [0ce418a]
|
|
88
|
+
- Updated dependencies [af90672]
|
|
89
|
+
- Updated dependencies [8387952]
|
|
90
|
+
- Updated dependencies [7f3b8da]
|
|
91
|
+
- Updated dependencies [905352b]
|
|
92
|
+
- Updated dependencies [599d04c]
|
|
93
|
+
- Updated dependencies [56041d0]
|
|
94
|
+
- Updated dependencies [3412597]
|
|
95
|
+
- Updated dependencies [5eca5d2]
|
|
96
|
+
- Updated dependencies [f2cda47]
|
|
97
|
+
- Updated dependencies [5de1555]
|
|
98
|
+
- Updated dependencies [cfd377a]
|
|
99
|
+
- Updated dependencies [1ed5a3e]
|
|
100
|
+
- @mastra/core@0.15.3
|
|
101
|
+
|
|
102
|
+
## 0.0.5-alpha.1
|
|
103
|
+
|
|
104
|
+
### Patch Changes
|
|
105
|
+
|
|
106
|
+
- [#7343](https://github.com/mastra-ai/mastra/pull/7343) [`de3cbc6`](https://github.com/mastra-ai/mastra/commit/de3cbc61079211431bd30487982ea3653517278e) Thanks [@LekoArts](https://github.com/LekoArts)! - Update the `package.json` file to include additional fields like `repository`, `homepage` or `files`.
|
|
107
|
+
|
|
108
|
+
- Updated dependencies [[`85ef90b`](https://github.com/mastra-ai/mastra/commit/85ef90bb2cd4ae4df855c7ac175f7d392c55c1bf), [`de3cbc6`](https://github.com/mastra-ai/mastra/commit/de3cbc61079211431bd30487982ea3653517278e)]:
|
|
109
|
+
- @mastra/core@0.15.3-alpha.5
|
|
110
|
+
|
|
111
|
+
## 0.0.5-alpha.0
|
|
112
|
+
|
|
113
|
+
### Patch Changes
|
|
114
|
+
|
|
115
|
+
- [#7266](https://github.com/mastra-ai/mastra/pull/7266) [`979912c`](https://github.com/mastra-ai/mastra/commit/979912cfd180aad53287cda08af771df26454e2c) Thanks [@epinzur](https://github.com/epinzur)! - "Updated langfuse exporter to handle Event spans"
|
|
116
|
+
|
|
117
|
+
- Updated dependencies [[`ab48c97`](https://github.com/mastra-ai/mastra/commit/ab48c979098ea571faf998a55d3a00e7acd7a715), [`ff89505`](https://github.com/mastra-ai/mastra/commit/ff895057c8c7e91a5535faef46c5e5391085ddfa), [`183dc95`](https://github.com/mastra-ai/mastra/commit/183dc95596f391b977bd1a2c050b8498dac74891), [`a1111e2`](https://github.com/mastra-ai/mastra/commit/a1111e24e705488adfe5e0a6f20c53bddf26cb22), [`61debef`](https://github.com/mastra-ai/mastra/commit/61debefd80ad3a7ed5737e19df6a23d40091689a), [`9beaeff`](https://github.com/mastra-ai/mastra/commit/9beaeffa4a97b1d5fd01a7f8af8708b16067f67c), [`9eee594`](https://github.com/mastra-ai/mastra/commit/9eee594e35e0ca2a650fcc33fa82009a142b9ed0), [`979912c`](https://github.com/mastra-ai/mastra/commit/979912cfd180aad53287cda08af771df26454e2c), [`7dcf4c0`](https://github.com/mastra-ai/mastra/commit/7dcf4c04f44d9345b1f8bc5d41eae3f11ac61611), [`ad78bfc`](https://github.com/mastra-ai/mastra/commit/ad78bfc4ea6a1fff140432bf4f638e01af7af668), [`0ce418a`](https://github.com/mastra-ai/mastra/commit/0ce418a1ccaa5e125d4483a9651b635046152569), [`8387952`](https://github.com/mastra-ai/mastra/commit/838795227b4edf758c84a2adf6f7fba206c27719), [`5eca5d2`](https://github.com/mastra-ai/mastra/commit/5eca5d2655788863ea0442a46c9ef5d3c6dbe0a8)]:
|
|
118
|
+
- @mastra/core@0.15.3-alpha.4
|
|
119
|
+
|
|
120
|
+
## 0.0.4
|
|
121
|
+
|
|
122
|
+
### Patch Changes
|
|
123
|
+
|
|
124
|
+
- [`c6113ed`](https://github.com/mastra-ai/mastra/commit/c6113ed7f9df297e130d94436ceee310273d6430) Thanks [@wardpeet](https://github.com/wardpeet)! - Fix peerdpes for @mastra/core
|
|
125
|
+
|
|
126
|
+
- Updated dependencies []:
|
|
127
|
+
- @mastra/core@0.15.2
|
|
128
|
+
|
|
129
|
+
## 0.0.3
|
|
130
|
+
|
|
131
|
+
### Patch Changes
|
|
132
|
+
|
|
133
|
+
- [`95b2aa9`](https://github.com/mastra-ai/mastra/commit/95b2aa908230919e67efcac0d69005a2d5745298) Thanks [@wardpeet](https://github.com/wardpeet)! - Fix peerdeps @mastra/core
|
|
134
|
+
|
|
135
|
+
- Updated dependencies []:
|
|
136
|
+
- @mastra/core@0.15.1
|
|
137
|
+
|
|
138
|
+
## 0.0.2
|
|
139
|
+
|
|
140
|
+
### Patch Changes
|
|
141
|
+
|
|
142
|
+
- 03997ae: Update peerdeps
|
|
143
|
+
- e1a81da: initial release of LangFuse AI Observability exporter
|
|
144
|
+
- Updated dependencies [227c7e6]
|
|
145
|
+
- Updated dependencies [12cae67]
|
|
146
|
+
- Updated dependencies [fd3a3eb]
|
|
147
|
+
- Updated dependencies [6faaee5]
|
|
148
|
+
- Updated dependencies [4232b14]
|
|
149
|
+
- Updated dependencies [a89de7e]
|
|
150
|
+
- Updated dependencies [5a37d0c]
|
|
151
|
+
- Updated dependencies [4bde0cb]
|
|
152
|
+
- Updated dependencies [cf4f357]
|
|
153
|
+
- Updated dependencies [ad888a2]
|
|
154
|
+
- Updated dependencies [481751d]
|
|
155
|
+
- Updated dependencies [2454423]
|
|
156
|
+
- Updated dependencies [194e395]
|
|
157
|
+
- Updated dependencies [a722c0b]
|
|
158
|
+
- Updated dependencies [c30bca8]
|
|
159
|
+
- Updated dependencies [3b5fec7]
|
|
160
|
+
- Updated dependencies [a8f129d]
|
|
161
|
+
- @mastra/core@0.14.0
|
|
162
|
+
|
|
163
|
+
## 0.0.2-alpha.1
|
|
164
|
+
|
|
165
|
+
### Patch Changes
|
|
166
|
+
|
|
167
|
+
- 03997ae: Update peerdeps
|
|
168
|
+
- @mastra/core@0.14.0-alpha.7
|
|
169
|
+
|
|
170
|
+
## 0.0.2-alpha.0
|
|
171
|
+
|
|
172
|
+
### Patch Changes
|
|
173
|
+
|
|
174
|
+
- e1a81da: initial release of LangFuse AI Observability exporter
|
|
175
|
+
- Updated dependencies [6faaee5]
|
|
176
|
+
- Updated dependencies [4232b14]
|
|
177
|
+
- Updated dependencies [a89de7e]
|
|
178
|
+
- Updated dependencies [cf4f357]
|
|
179
|
+
- Updated dependencies [a722c0b]
|
|
180
|
+
- Updated dependencies [3b5fec7]
|
|
181
|
+
- @mastra/core@0.14.0-alpha.1
|
package/LICENSE.md
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# Apache License 2.0
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 Kepler Software, Inc.
|
|
4
|
+
|
|
5
|
+
Licensed under the Apache License, Version 2.0 (the "License");
|
|
6
|
+
you may not use this file except in compliance with the License.
|
|
7
|
+
You may obtain a copy of the License at
|
|
8
|
+
|
|
9
|
+
http://www.apache.org/licenses/LICENSE-2.0
|
|
10
|
+
|
|
11
|
+
Unless required by applicable law or agreed to in writing, software
|
|
12
|
+
distributed under the License is distributed on an "AS IS" BASIS,
|
|
13
|
+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
14
|
+
See the License for the specific language governing permissions and
|
|
15
|
+
limitations under the License.
|
package/README.md
ADDED
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
# @mastra/langfuse
|
|
2
|
+
|
|
3
|
+
Langfuse AI Observability exporter for Mastra applications.
|
|
4
|
+
|
|
5
|
+
## Installation
|
|
6
|
+
|
|
7
|
+
```bash
|
|
8
|
+
npm install @mastra/langfuse
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## Usage
|
|
12
|
+
|
|
13
|
+
```typescript
|
|
14
|
+
import { LangfuseExporter } from '@mastra/langfuse';
|
|
15
|
+
|
|
16
|
+
// Use with Mastra
|
|
17
|
+
const mastra = new Mastra({
|
|
18
|
+
...,
|
|
19
|
+
observability: {
|
|
20
|
+
configs: {
|
|
21
|
+
langfuse: {
|
|
22
|
+
serviceName: 'service',
|
|
23
|
+
exporters: [
|
|
24
|
+
new LangfuseExporter({
|
|
25
|
+
publicKey: process.env.LANGFUSE_PUBLIC_KEY,
|
|
26
|
+
secretKey: process.env.LANGFUSE_SECRET_KEY,
|
|
27
|
+
baseUrl: process.env.LANGFUSE_BASE_URL, // Optional - defaults to Langfuse cloud
|
|
28
|
+
realtime: true,
|
|
29
|
+
}),
|
|
30
|
+
],
|
|
31
|
+
},
|
|
32
|
+
},
|
|
33
|
+
},
|
|
34
|
+
});
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
## Features
|
|
38
|
+
|
|
39
|
+
### AI Tracing
|
|
40
|
+
|
|
41
|
+
- **Automatic span mapping**: Root spans become Langfuse traces
|
|
42
|
+
- **LLM generation support**: `LLM_GENERATION` spans become Langfuse generations with token usage
|
|
43
|
+
- **Type-specific metadata**: Extracts relevant metadata for each span type (agents, tools, workflows)
|
|
44
|
+
- **Error tracking**: Automatic error status and message tracking
|
|
45
|
+
- **Hierarchical traces**: Maintains parent-child relationships
|
|
46
|
+
|
|
47
|
+
## License
|
|
48
|
+
|
|
49
|
+
Apache 2.0
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Langfuse Exporter for Mastra AI Tracing
|
|
3
|
+
*
|
|
4
|
+
* This exporter sends tracing data to Langfuse for AI observability.
|
|
5
|
+
* Root spans start traces in Langfuse.
|
|
6
|
+
* LLM_GENERATION spans become Langfuse generations, all others become spans.
|
|
7
|
+
*/
|
|
8
|
+
import type { AITracingExporter, AITracingEvent } from '@mastra/core/ai-tracing';
|
|
9
|
+
export interface LangfuseExporterConfig {
|
|
10
|
+
/** Langfuse API key */
|
|
11
|
+
publicKey?: string;
|
|
12
|
+
/** Langfuse secret key */
|
|
13
|
+
secretKey?: string;
|
|
14
|
+
/** Langfuse host URL */
|
|
15
|
+
baseUrl?: string;
|
|
16
|
+
/** Enable realtime mode - flushes after each event for immediate visibility */
|
|
17
|
+
realtime?: boolean;
|
|
18
|
+
/** Logger level for diagnostic messages (default: 'warn') */
|
|
19
|
+
logLevel?: 'debug' | 'info' | 'warn' | 'error';
|
|
20
|
+
/** Additional options to pass to the Langfuse client */
|
|
21
|
+
options?: any;
|
|
22
|
+
}
|
|
23
|
+
export declare class LangfuseExporter implements AITracingExporter {
|
|
24
|
+
name: string;
|
|
25
|
+
private client;
|
|
26
|
+
private realtime;
|
|
27
|
+
private traceMap;
|
|
28
|
+
private logger;
|
|
29
|
+
constructor(config: LangfuseExporterConfig);
|
|
30
|
+
exportEvent(event: AITracingEvent): Promise<void>;
|
|
31
|
+
private handleSpanStarted;
|
|
32
|
+
private handleSpanUpdateOrEnd;
|
|
33
|
+
private handleEventSpan;
|
|
34
|
+
private initTrace;
|
|
35
|
+
private getTraceData;
|
|
36
|
+
private getLangfuseParent;
|
|
37
|
+
private buildTracePayload;
|
|
38
|
+
private buildSpanPayload;
|
|
39
|
+
shutdown(): Promise<void>;
|
|
40
|
+
}
|
|
41
|
+
//# sourceMappingURL=ai-tracing.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ai-tracing.d.ts","sourceRoot":"","sources":["../src/ai-tracing.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,EAAE,iBAAiB,EAAE,cAAc,EAAsC,MAAM,yBAAyB,CAAC;AAMrH,MAAM,WAAW,sBAAsB;IACrC,uBAAuB;IACvB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,0BAA0B;IAC1B,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,wBAAwB;IACxB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,+EAA+E;IAC/E,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,6DAA6D;IAC7D,QAAQ,CAAC,EAAE,OAAO,GAAG,MAAM,GAAG,MAAM,GAAG,OAAO,CAAC;IAC/C,wDAAwD;IACxD,OAAO,CAAC,EAAE,GAAG,CAAC;CACf;AAUD,qBAAa,gBAAiB,YAAW,iBAAiB;IACxD,IAAI,SAAc;IAClB,OAAO,CAAC,MAAM,CAAW;IACzB,OAAO,CAAC,QAAQ,CAAU;IAC1B,OAAO,CAAC,QAAQ,CAAgC;IAChD,OAAO,CAAC,MAAM,CAAgB;gBAElB,MAAM,EAAE,sBAAsB;IAsBpC,WAAW,CAAC,KAAK,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC;YA6BzC,iBAAiB;YAwBjB,qBAAqB;YAgCrB,eAAe;IA6B7B,OAAO,CAAC,SAAS;IAKjB,OAAO,CAAC,YAAY;IAgBpB,OAAO,CAAC,iBAAiB;IA4BzB,OAAO,CAAC,iBAAiB;IAqBzB,OAAO,CAAC,gBAAgB;IAmDlB,QAAQ,IAAI,OAAO,CAAC,IAAI,CAAC;CAMhC"}
|
package/dist/index.cjs
ADDED
|
@@ -0,0 +1,225 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var aiTracing = require('@mastra/core/ai-tracing');
|
|
4
|
+
var logger = require('@mastra/core/logger');
|
|
5
|
+
var langfuse = require('langfuse');
|
|
6
|
+
|
|
7
|
+
// src/ai-tracing.ts
|
|
8
|
+
var LangfuseExporter = class {
|
|
9
|
+
name = "langfuse";
|
|
10
|
+
client;
|
|
11
|
+
realtime;
|
|
12
|
+
traceMap = /* @__PURE__ */ new Map();
|
|
13
|
+
logger;
|
|
14
|
+
constructor(config) {
|
|
15
|
+
this.realtime = config.realtime ?? false;
|
|
16
|
+
this.logger = new logger.ConsoleLogger({ level: config.logLevel ?? "warn" });
|
|
17
|
+
if (!config.publicKey || !config.secretKey) {
|
|
18
|
+
this.logger.error("LangfuseExporter: Missing required credentials, exporter will be disabled", {
|
|
19
|
+
hasPublicKey: !!config.publicKey,
|
|
20
|
+
hasSecretKey: !!config.secretKey
|
|
21
|
+
});
|
|
22
|
+
this.client = null;
|
|
23
|
+
return;
|
|
24
|
+
}
|
|
25
|
+
this.client = new langfuse.Langfuse({
|
|
26
|
+
publicKey: config.publicKey,
|
|
27
|
+
secretKey: config.secretKey,
|
|
28
|
+
baseUrl: config.baseUrl,
|
|
29
|
+
...config.options
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
async exportEvent(event) {
|
|
33
|
+
if (!this.client) {
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
if (event.span.isEvent) {
|
|
37
|
+
await this.handleEventSpan(event.span);
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
switch (event.type) {
|
|
41
|
+
case "span_started":
|
|
42
|
+
await this.handleSpanStarted(event.span);
|
|
43
|
+
break;
|
|
44
|
+
case "span_updated":
|
|
45
|
+
await this.handleSpanUpdateOrEnd(event.span, false);
|
|
46
|
+
break;
|
|
47
|
+
case "span_ended":
|
|
48
|
+
await this.handleSpanUpdateOrEnd(event.span, true);
|
|
49
|
+
break;
|
|
50
|
+
}
|
|
51
|
+
if (this.realtime) {
|
|
52
|
+
await this.client.flushAsync();
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
async handleSpanStarted(span) {
|
|
56
|
+
if (span.isRootSpan) {
|
|
57
|
+
this.initTrace(span);
|
|
58
|
+
}
|
|
59
|
+
const method = "handleSpanStarted";
|
|
60
|
+
const traceData = this.getTraceData({ span, method });
|
|
61
|
+
if (!traceData) {
|
|
62
|
+
return;
|
|
63
|
+
}
|
|
64
|
+
const langfuseParent = this.getLangfuseParent({ traceData, span, method });
|
|
65
|
+
if (!langfuseParent) {
|
|
66
|
+
return;
|
|
67
|
+
}
|
|
68
|
+
const payload = this.buildSpanPayload(span, true);
|
|
69
|
+
const langfuseSpan = span.type === aiTracing.AISpanType.LLM_GENERATION ? langfuseParent.generation(payload) : langfuseParent.span(payload);
|
|
70
|
+
traceData.spans.set(span.id, langfuseSpan);
|
|
71
|
+
}
|
|
72
|
+
async handleSpanUpdateOrEnd(span, isEnd) {
|
|
73
|
+
const method = isEnd ? "handleSpanEnd" : "handleSpanUpdate";
|
|
74
|
+
const traceData = this.getTraceData({ span, method });
|
|
75
|
+
if (!traceData) {
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
const langfuseSpan = traceData.spans.get(span.id);
|
|
79
|
+
if (!langfuseSpan) {
|
|
80
|
+
this.logger.warn("Langfuse exporter: No Langfuse span found for span update/end", {
|
|
81
|
+
traceId: span.traceId,
|
|
82
|
+
spanId: span.id,
|
|
83
|
+
spanName: span.name,
|
|
84
|
+
spanType: span.type,
|
|
85
|
+
isRootSpan: span.isRootSpan,
|
|
86
|
+
parentSpanId: span.parent?.id,
|
|
87
|
+
method
|
|
88
|
+
});
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
langfuseSpan.update(this.buildSpanPayload(span, false));
|
|
92
|
+
if (isEnd && span.isRootSpan) {
|
|
93
|
+
traceData.trace.update({ output: span.output });
|
|
94
|
+
this.traceMap.delete(span.traceId);
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
async handleEventSpan(span) {
|
|
98
|
+
if (span.isRootSpan) {
|
|
99
|
+
this.logger.debug("Langfuse exporter: Creating trace", {
|
|
100
|
+
traceId: span.traceId,
|
|
101
|
+
spanId: span.id,
|
|
102
|
+
spanName: span.name,
|
|
103
|
+
method: "handleEventSpan"
|
|
104
|
+
});
|
|
105
|
+
this.initTrace(span);
|
|
106
|
+
}
|
|
107
|
+
const method = "handleEventSpan";
|
|
108
|
+
const traceData = this.getTraceData({ span, method });
|
|
109
|
+
if (!traceData) {
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
const langfuseParent = this.getLangfuseParent({ traceData, span, method });
|
|
113
|
+
if (!langfuseParent) {
|
|
114
|
+
return;
|
|
115
|
+
}
|
|
116
|
+
const payload = this.buildSpanPayload(span, true);
|
|
117
|
+
const langfuseEvent = langfuseParent.event(payload);
|
|
118
|
+
traceData.events.set(span.id, langfuseEvent);
|
|
119
|
+
}
|
|
120
|
+
initTrace(span) {
|
|
121
|
+
const trace = this.client.trace(this.buildTracePayload(span));
|
|
122
|
+
this.traceMap.set(span.traceId, { trace, spans: /* @__PURE__ */ new Map(), events: /* @__PURE__ */ new Map() });
|
|
123
|
+
}
|
|
124
|
+
getTraceData(options) {
|
|
125
|
+
const { span, method } = options;
|
|
126
|
+
if (this.traceMap.has(span.traceId)) {
|
|
127
|
+
return this.traceMap.get(span.traceId);
|
|
128
|
+
}
|
|
129
|
+
this.logger.warn("Langfuse exporter: No trace data found for span", {
|
|
130
|
+
traceId: span.traceId,
|
|
131
|
+
spanId: span.id,
|
|
132
|
+
spanName: span.name,
|
|
133
|
+
spanType: span.type,
|
|
134
|
+
isRootSpan: span.isRootSpan,
|
|
135
|
+
parentSpanId: span.parent?.id,
|
|
136
|
+
method
|
|
137
|
+
});
|
|
138
|
+
}
|
|
139
|
+
getLangfuseParent(options) {
|
|
140
|
+
const { traceData, span, method } = options;
|
|
141
|
+
const parentId = span.parent?.id;
|
|
142
|
+
if (!parentId) {
|
|
143
|
+
return traceData.trace;
|
|
144
|
+
}
|
|
145
|
+
if (traceData.spans.has(parentId)) {
|
|
146
|
+
return traceData.spans.get(parentId);
|
|
147
|
+
}
|
|
148
|
+
if (traceData.events.has(parentId)) {
|
|
149
|
+
return traceData.events.get(parentId);
|
|
150
|
+
}
|
|
151
|
+
this.logger.warn("Langfuse exporter: No parent data found for span", {
|
|
152
|
+
traceId: span.traceId,
|
|
153
|
+
spanId: span.id,
|
|
154
|
+
spanName: span.name,
|
|
155
|
+
spanType: span.type,
|
|
156
|
+
isRootSpan: span.isRootSpan,
|
|
157
|
+
parentSpanId: span.parent?.id,
|
|
158
|
+
method
|
|
159
|
+
});
|
|
160
|
+
}
|
|
161
|
+
buildTracePayload(span) {
|
|
162
|
+
const payload = {
|
|
163
|
+
id: span.traceId,
|
|
164
|
+
name: span.name
|
|
165
|
+
};
|
|
166
|
+
const { userId, sessionId, ...remainingMetadata } = span.metadata ?? {};
|
|
167
|
+
if (userId) payload.userId = userId;
|
|
168
|
+
if (sessionId) payload.sessionId = sessionId;
|
|
169
|
+
if (span.input) payload.input = span.input;
|
|
170
|
+
payload.metadata = {
|
|
171
|
+
spanType: span.type,
|
|
172
|
+
...span.attributes,
|
|
173
|
+
...remainingMetadata
|
|
174
|
+
};
|
|
175
|
+
return payload;
|
|
176
|
+
}
|
|
177
|
+
buildSpanPayload(span, isCreate) {
|
|
178
|
+
const payload = {};
|
|
179
|
+
if (isCreate) {
|
|
180
|
+
payload.id = span.id;
|
|
181
|
+
payload.name = span.name;
|
|
182
|
+
payload.startTime = span.startTime;
|
|
183
|
+
if (span.input !== void 0) payload.input = span.input;
|
|
184
|
+
}
|
|
185
|
+
if (span.output !== void 0) payload.output = span.output;
|
|
186
|
+
if (span.endTime !== void 0) payload.endTime = span.endTime;
|
|
187
|
+
const attributes = span.attributes ?? {};
|
|
188
|
+
const attributesToOmit = [];
|
|
189
|
+
if (span.type === aiTracing.AISpanType.LLM_GENERATION) {
|
|
190
|
+
const llmAttr = attributes;
|
|
191
|
+
if (llmAttr.model !== void 0) {
|
|
192
|
+
payload.model = llmAttr.model;
|
|
193
|
+
attributesToOmit.push("model");
|
|
194
|
+
}
|
|
195
|
+
if (llmAttr.usage !== void 0) {
|
|
196
|
+
payload.usage = llmAttr.usage;
|
|
197
|
+
attributesToOmit.push("usage");
|
|
198
|
+
}
|
|
199
|
+
if (llmAttr.parameters !== void 0) {
|
|
200
|
+
payload.modelParameters = llmAttr.parameters;
|
|
201
|
+
attributesToOmit.push("parameters");
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
payload.metadata = {
|
|
205
|
+
spanType: span.type,
|
|
206
|
+
...aiTracing.omitKeys(attributes, attributesToOmit),
|
|
207
|
+
...span.metadata
|
|
208
|
+
};
|
|
209
|
+
if (span.errorInfo) {
|
|
210
|
+
payload.level = "ERROR";
|
|
211
|
+
payload.statusMessage = span.errorInfo.message;
|
|
212
|
+
}
|
|
213
|
+
return payload;
|
|
214
|
+
}
|
|
215
|
+
async shutdown() {
|
|
216
|
+
if (this.client) {
|
|
217
|
+
await this.client.shutdownAsync();
|
|
218
|
+
}
|
|
219
|
+
this.traceMap.clear();
|
|
220
|
+
}
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
exports.LangfuseExporter = LangfuseExporter;
|
|
224
|
+
//# sourceMappingURL=index.cjs.map
|
|
225
|
+
//# sourceMappingURL=index.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/ai-tracing.ts"],"names":["ConsoleLogger","Langfuse","AISpanType","omitKeys"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Langfuse Exporter for Mastra AI Tracing\n *\n * This exporter sends tracing data to Langfuse for AI observability.\n * Root spans start traces in Langfuse.\n * LLM_GENERATION spans become Langfuse generations, all others become spans.\n */\n\nimport type { AITracingExporter, AITracingEvent, AnyAISpan, LLMGenerationAttributes } from '@mastra/core/ai-tracing';\nimport { AISpanType, omitKeys } from '@mastra/core/ai-tracing';\nimport { ConsoleLogger } from '@mastra/core/logger';\nimport { Langfuse } from 'langfuse';\nimport type { LangfuseTraceClient, LangfuseSpanClient, LangfuseGenerationClient, LangfuseEventClient } from 'langfuse';\n\nexport interface LangfuseExporterConfig {\n /** Langfuse API key */\n publicKey?: string;\n /** Langfuse secret key */\n secretKey?: string;\n /** Langfuse host URL */\n baseUrl?: string;\n /** Enable realtime mode - flushes after each event for immediate visibility */\n realtime?: boolean;\n /** Logger level for diagnostic messages (default: 'warn') */\n logLevel?: 'debug' | 'info' | 'warn' | 'error';\n /** Additional options to pass to the Langfuse client */\n options?: any;\n}\n\ntype TraceData = {\n trace: LangfuseTraceClient; // Langfuse trace object\n spans: Map<string, LangfuseSpanClient | LangfuseGenerationClient>; // Maps span.id to Langfuse span/generation\n events: Map<string, LangfuseEventClient>; // Maps span.id to Langfuse event\n};\n\ntype LangfuseParent = LangfuseTraceClient | LangfuseSpanClient | LangfuseGenerationClient | LangfuseEventClient;\n\nexport class LangfuseExporter implements AITracingExporter {\n name = 'langfuse';\n private client: Langfuse;\n private realtime: boolean;\n private traceMap = new Map<string, TraceData>();\n private logger: ConsoleLogger;\n\n constructor(config: LangfuseExporterConfig) {\n this.realtime = config.realtime ?? false;\n this.logger = new ConsoleLogger({ level: config.logLevel ?? 'warn' });\n\n if (!config.publicKey || !config.secretKey) {\n this.logger.error('LangfuseExporter: Missing required credentials, exporter will be disabled', {\n hasPublicKey: !!config.publicKey,\n hasSecretKey: !!config.secretKey,\n });\n // Create a no-op client to prevent runtime errors\n this.client = null as any;\n return;\n }\n\n this.client = new Langfuse({\n publicKey: config.publicKey,\n secretKey: config.secretKey,\n baseUrl: config.baseUrl,\n ...config.options,\n });\n }\n\n async exportEvent(event: AITracingEvent): Promise<void> {\n if (!this.client) {\n // Exporter is disabled due to missing credentials\n return;\n }\n\n if (event.span.isEvent) {\n await this.handleEventSpan(event.span);\n return;\n }\n\n switch (event.type) {\n case 'span_started':\n await this.handleSpanStarted(event.span);\n break;\n case 'span_updated':\n await this.handleSpanUpdateOrEnd(event.span, false);\n break;\n case 'span_ended':\n await this.handleSpanUpdateOrEnd(event.span, true);\n break;\n }\n\n // Flush immediately in realtime mode for instant visibility\n if (this.realtime) {\n await this.client.flushAsync();\n }\n }\n\n private async handleSpanStarted(span: AnyAISpan): Promise<void> {\n if (span.isRootSpan) {\n this.initTrace(span);\n }\n const method = 'handleSpanStarted';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseParent = this.getLangfuseParent({ traceData, span, method });\n if (!langfuseParent) {\n return;\n }\n\n const payload = this.buildSpanPayload(span, true);\n\n const langfuseSpan =\n span.type === AISpanType.LLM_GENERATION ? langfuseParent.generation(payload) : langfuseParent.span(payload);\n\n traceData.spans.set(span.id, langfuseSpan);\n }\n\n private async handleSpanUpdateOrEnd(span: AnyAISpan, isEnd: boolean): Promise<void> {\n const method = isEnd ? 'handleSpanEnd' : 'handleSpanUpdate';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseSpan = traceData.spans.get(span.id);\n if (!langfuseSpan) {\n this.logger.warn('Langfuse exporter: No Langfuse span found for span update/end', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n return;\n }\n\n // use update for both update & end, so that we can use the\n // end time we set when ending the span.\n langfuseSpan.update(this.buildSpanPayload(span, false));\n\n if (isEnd && span.isRootSpan) {\n traceData.trace.update({ output: span.output });\n this.traceMap.delete(span.traceId);\n }\n }\n\n private async handleEventSpan(span: AnyAISpan): Promise<void> {\n if (span.isRootSpan) {\n this.logger.debug('Langfuse exporter: Creating trace', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n method: 'handleEventSpan',\n });\n this.initTrace(span);\n }\n const method = 'handleEventSpan';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseParent = this.getLangfuseParent({ traceData, span, method });\n if (!langfuseParent) {\n return;\n }\n\n const payload = this.buildSpanPayload(span, true);\n\n const langfuseEvent = langfuseParent.event(payload);\n\n traceData.events.set(span.id, langfuseEvent);\n }\n\n private initTrace(span: AnyAISpan): void {\n const trace = this.client.trace(this.buildTracePayload(span));\n this.traceMap.set(span.traceId, { trace, spans: new Map(), events: new Map() });\n }\n\n private getTraceData(options: { span: AnyAISpan; method: string }): TraceData | undefined {\n const { span, method } = options;\n if (this.traceMap.has(span.traceId)) {\n return this.traceMap.get(span.traceId);\n }\n this.logger.warn('Langfuse exporter: No trace data found for span', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n }\n\n private getLangfuseParent(options: {\n traceData: TraceData;\n span: AnyAISpan;\n method: string;\n }): LangfuseParent | undefined {\n const { traceData, span, method } = options;\n\n const parentId = span.parent?.id;\n if (!parentId) {\n return traceData.trace;\n }\n if (traceData.spans.has(parentId)) {\n return traceData.spans.get(parentId);\n }\n if (traceData.events.has(parentId)) {\n return traceData.events.get(parentId);\n }\n this.logger.warn('Langfuse exporter: No parent data found for span', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n }\n\n private buildTracePayload(span: AnyAISpan): Record<string, any> {\n const payload: Record<string, any> = {\n id: span.traceId,\n name: span.name,\n };\n\n const { userId, sessionId, ...remainingMetadata } = span.metadata ?? {};\n\n if (userId) payload.userId = userId;\n if (sessionId) payload.sessionId = sessionId;\n if (span.input) payload.input = span.input;\n\n payload.metadata = {\n spanType: span.type,\n ...span.attributes,\n ...remainingMetadata,\n };\n\n return payload;\n }\n\n private buildSpanPayload(span: AnyAISpan, isCreate: boolean): Record<string, any> {\n const payload: Record<string, any> = {};\n\n if (isCreate) {\n payload.id = span.id;\n payload.name = span.name;\n payload.startTime = span.startTime;\n if (span.input !== undefined) payload.input = span.input;\n }\n\n if (span.output !== undefined) payload.output = span.output;\n if (span.endTime !== undefined) payload.endTime = span.endTime;\n\n const attributes = (span.attributes ?? {}) as Record<string, any>;\n\n // Strip special fields from metadata if used in top-level keys\n const attributesToOmit: string[] = [];\n\n if (span.type === AISpanType.LLM_GENERATION) {\n const llmAttr = attributes as LLMGenerationAttributes;\n\n if (llmAttr.model !== undefined) {\n payload.model = llmAttr.model;\n attributesToOmit.push('model');\n }\n\n if (llmAttr.usage !== undefined) {\n payload.usage = llmAttr.usage;\n attributesToOmit.push('usage');\n }\n\n if (llmAttr.parameters !== undefined) {\n payload.modelParameters = llmAttr.parameters;\n attributesToOmit.push('parameters');\n }\n }\n\n payload.metadata = {\n spanType: span.type,\n ...omitKeys(attributes, attributesToOmit),\n ...span.metadata,\n };\n\n if (span.errorInfo) {\n payload.level = 'ERROR';\n payload.statusMessage = span.errorInfo.message;\n }\n\n return payload;\n }\n\n async shutdown(): Promise<void> {\n if (this.client) {\n await this.client.shutdownAsync();\n }\n this.traceMap.clear();\n }\n}\n"]}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Langfuse Observability Provider for Mastra
|
|
3
|
+
*
|
|
4
|
+
* This package provides Langfuse-specific observability features for Mastra applications.
|
|
5
|
+
* Currently includes AI tracing support with plans for additional observability features.
|
|
6
|
+
*/
|
|
7
|
+
export * from './ai-tracing.js';
|
|
8
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,cAAc,cAAc,CAAC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,223 @@
|
|
|
1
|
+
import { AISpanType, omitKeys } from '@mastra/core/ai-tracing';
|
|
2
|
+
import { ConsoleLogger } from '@mastra/core/logger';
|
|
3
|
+
import { Langfuse } from 'langfuse';
|
|
4
|
+
|
|
5
|
+
// src/ai-tracing.ts
|
|
6
|
+
var LangfuseExporter = class {
|
|
7
|
+
name = "langfuse";
|
|
8
|
+
client;
|
|
9
|
+
realtime;
|
|
10
|
+
traceMap = /* @__PURE__ */ new Map();
|
|
11
|
+
logger;
|
|
12
|
+
constructor(config) {
|
|
13
|
+
this.realtime = config.realtime ?? false;
|
|
14
|
+
this.logger = new ConsoleLogger({ level: config.logLevel ?? "warn" });
|
|
15
|
+
if (!config.publicKey || !config.secretKey) {
|
|
16
|
+
this.logger.error("LangfuseExporter: Missing required credentials, exporter will be disabled", {
|
|
17
|
+
hasPublicKey: !!config.publicKey,
|
|
18
|
+
hasSecretKey: !!config.secretKey
|
|
19
|
+
});
|
|
20
|
+
this.client = null;
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
this.client = new Langfuse({
|
|
24
|
+
publicKey: config.publicKey,
|
|
25
|
+
secretKey: config.secretKey,
|
|
26
|
+
baseUrl: config.baseUrl,
|
|
27
|
+
...config.options
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
async exportEvent(event) {
|
|
31
|
+
if (!this.client) {
|
|
32
|
+
return;
|
|
33
|
+
}
|
|
34
|
+
if (event.span.isEvent) {
|
|
35
|
+
await this.handleEventSpan(event.span);
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
switch (event.type) {
|
|
39
|
+
case "span_started":
|
|
40
|
+
await this.handleSpanStarted(event.span);
|
|
41
|
+
break;
|
|
42
|
+
case "span_updated":
|
|
43
|
+
await this.handleSpanUpdateOrEnd(event.span, false);
|
|
44
|
+
break;
|
|
45
|
+
case "span_ended":
|
|
46
|
+
await this.handleSpanUpdateOrEnd(event.span, true);
|
|
47
|
+
break;
|
|
48
|
+
}
|
|
49
|
+
if (this.realtime) {
|
|
50
|
+
await this.client.flushAsync();
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
async handleSpanStarted(span) {
|
|
54
|
+
if (span.isRootSpan) {
|
|
55
|
+
this.initTrace(span);
|
|
56
|
+
}
|
|
57
|
+
const method = "handleSpanStarted";
|
|
58
|
+
const traceData = this.getTraceData({ span, method });
|
|
59
|
+
if (!traceData) {
|
|
60
|
+
return;
|
|
61
|
+
}
|
|
62
|
+
const langfuseParent = this.getLangfuseParent({ traceData, span, method });
|
|
63
|
+
if (!langfuseParent) {
|
|
64
|
+
return;
|
|
65
|
+
}
|
|
66
|
+
const payload = this.buildSpanPayload(span, true);
|
|
67
|
+
const langfuseSpan = span.type === AISpanType.LLM_GENERATION ? langfuseParent.generation(payload) : langfuseParent.span(payload);
|
|
68
|
+
traceData.spans.set(span.id, langfuseSpan);
|
|
69
|
+
}
|
|
70
|
+
async handleSpanUpdateOrEnd(span, isEnd) {
|
|
71
|
+
const method = isEnd ? "handleSpanEnd" : "handleSpanUpdate";
|
|
72
|
+
const traceData = this.getTraceData({ span, method });
|
|
73
|
+
if (!traceData) {
|
|
74
|
+
return;
|
|
75
|
+
}
|
|
76
|
+
const langfuseSpan = traceData.spans.get(span.id);
|
|
77
|
+
if (!langfuseSpan) {
|
|
78
|
+
this.logger.warn("Langfuse exporter: No Langfuse span found for span update/end", {
|
|
79
|
+
traceId: span.traceId,
|
|
80
|
+
spanId: span.id,
|
|
81
|
+
spanName: span.name,
|
|
82
|
+
spanType: span.type,
|
|
83
|
+
isRootSpan: span.isRootSpan,
|
|
84
|
+
parentSpanId: span.parent?.id,
|
|
85
|
+
method
|
|
86
|
+
});
|
|
87
|
+
return;
|
|
88
|
+
}
|
|
89
|
+
langfuseSpan.update(this.buildSpanPayload(span, false));
|
|
90
|
+
if (isEnd && span.isRootSpan) {
|
|
91
|
+
traceData.trace.update({ output: span.output });
|
|
92
|
+
this.traceMap.delete(span.traceId);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
async handleEventSpan(span) {
|
|
96
|
+
if (span.isRootSpan) {
|
|
97
|
+
this.logger.debug("Langfuse exporter: Creating trace", {
|
|
98
|
+
traceId: span.traceId,
|
|
99
|
+
spanId: span.id,
|
|
100
|
+
spanName: span.name,
|
|
101
|
+
method: "handleEventSpan"
|
|
102
|
+
});
|
|
103
|
+
this.initTrace(span);
|
|
104
|
+
}
|
|
105
|
+
const method = "handleEventSpan";
|
|
106
|
+
const traceData = this.getTraceData({ span, method });
|
|
107
|
+
if (!traceData) {
|
|
108
|
+
return;
|
|
109
|
+
}
|
|
110
|
+
const langfuseParent = this.getLangfuseParent({ traceData, span, method });
|
|
111
|
+
if (!langfuseParent) {
|
|
112
|
+
return;
|
|
113
|
+
}
|
|
114
|
+
const payload = this.buildSpanPayload(span, true);
|
|
115
|
+
const langfuseEvent = langfuseParent.event(payload);
|
|
116
|
+
traceData.events.set(span.id, langfuseEvent);
|
|
117
|
+
}
|
|
118
|
+
initTrace(span) {
|
|
119
|
+
const trace = this.client.trace(this.buildTracePayload(span));
|
|
120
|
+
this.traceMap.set(span.traceId, { trace, spans: /* @__PURE__ */ new Map(), events: /* @__PURE__ */ new Map() });
|
|
121
|
+
}
|
|
122
|
+
getTraceData(options) {
|
|
123
|
+
const { span, method } = options;
|
|
124
|
+
if (this.traceMap.has(span.traceId)) {
|
|
125
|
+
return this.traceMap.get(span.traceId);
|
|
126
|
+
}
|
|
127
|
+
this.logger.warn("Langfuse exporter: No trace data found for span", {
|
|
128
|
+
traceId: span.traceId,
|
|
129
|
+
spanId: span.id,
|
|
130
|
+
spanName: span.name,
|
|
131
|
+
spanType: span.type,
|
|
132
|
+
isRootSpan: span.isRootSpan,
|
|
133
|
+
parentSpanId: span.parent?.id,
|
|
134
|
+
method
|
|
135
|
+
});
|
|
136
|
+
}
|
|
137
|
+
getLangfuseParent(options) {
|
|
138
|
+
const { traceData, span, method } = options;
|
|
139
|
+
const parentId = span.parent?.id;
|
|
140
|
+
if (!parentId) {
|
|
141
|
+
return traceData.trace;
|
|
142
|
+
}
|
|
143
|
+
if (traceData.spans.has(parentId)) {
|
|
144
|
+
return traceData.spans.get(parentId);
|
|
145
|
+
}
|
|
146
|
+
if (traceData.events.has(parentId)) {
|
|
147
|
+
return traceData.events.get(parentId);
|
|
148
|
+
}
|
|
149
|
+
this.logger.warn("Langfuse exporter: No parent data found for span", {
|
|
150
|
+
traceId: span.traceId,
|
|
151
|
+
spanId: span.id,
|
|
152
|
+
spanName: span.name,
|
|
153
|
+
spanType: span.type,
|
|
154
|
+
isRootSpan: span.isRootSpan,
|
|
155
|
+
parentSpanId: span.parent?.id,
|
|
156
|
+
method
|
|
157
|
+
});
|
|
158
|
+
}
|
|
159
|
+
buildTracePayload(span) {
|
|
160
|
+
const payload = {
|
|
161
|
+
id: span.traceId,
|
|
162
|
+
name: span.name
|
|
163
|
+
};
|
|
164
|
+
const { userId, sessionId, ...remainingMetadata } = span.metadata ?? {};
|
|
165
|
+
if (userId) payload.userId = userId;
|
|
166
|
+
if (sessionId) payload.sessionId = sessionId;
|
|
167
|
+
if (span.input) payload.input = span.input;
|
|
168
|
+
payload.metadata = {
|
|
169
|
+
spanType: span.type,
|
|
170
|
+
...span.attributes,
|
|
171
|
+
...remainingMetadata
|
|
172
|
+
};
|
|
173
|
+
return payload;
|
|
174
|
+
}
|
|
175
|
+
buildSpanPayload(span, isCreate) {
|
|
176
|
+
const payload = {};
|
|
177
|
+
if (isCreate) {
|
|
178
|
+
payload.id = span.id;
|
|
179
|
+
payload.name = span.name;
|
|
180
|
+
payload.startTime = span.startTime;
|
|
181
|
+
if (span.input !== void 0) payload.input = span.input;
|
|
182
|
+
}
|
|
183
|
+
if (span.output !== void 0) payload.output = span.output;
|
|
184
|
+
if (span.endTime !== void 0) payload.endTime = span.endTime;
|
|
185
|
+
const attributes = span.attributes ?? {};
|
|
186
|
+
const attributesToOmit = [];
|
|
187
|
+
if (span.type === AISpanType.LLM_GENERATION) {
|
|
188
|
+
const llmAttr = attributes;
|
|
189
|
+
if (llmAttr.model !== void 0) {
|
|
190
|
+
payload.model = llmAttr.model;
|
|
191
|
+
attributesToOmit.push("model");
|
|
192
|
+
}
|
|
193
|
+
if (llmAttr.usage !== void 0) {
|
|
194
|
+
payload.usage = llmAttr.usage;
|
|
195
|
+
attributesToOmit.push("usage");
|
|
196
|
+
}
|
|
197
|
+
if (llmAttr.parameters !== void 0) {
|
|
198
|
+
payload.modelParameters = llmAttr.parameters;
|
|
199
|
+
attributesToOmit.push("parameters");
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
payload.metadata = {
|
|
203
|
+
spanType: span.type,
|
|
204
|
+
...omitKeys(attributes, attributesToOmit),
|
|
205
|
+
...span.metadata
|
|
206
|
+
};
|
|
207
|
+
if (span.errorInfo) {
|
|
208
|
+
payload.level = "ERROR";
|
|
209
|
+
payload.statusMessage = span.errorInfo.message;
|
|
210
|
+
}
|
|
211
|
+
return payload;
|
|
212
|
+
}
|
|
213
|
+
async shutdown() {
|
|
214
|
+
if (this.client) {
|
|
215
|
+
await this.client.shutdownAsync();
|
|
216
|
+
}
|
|
217
|
+
this.traceMap.clear();
|
|
218
|
+
}
|
|
219
|
+
};
|
|
220
|
+
|
|
221
|
+
export { LangfuseExporter };
|
|
222
|
+
//# sourceMappingURL=index.js.map
|
|
223
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/ai-tracing.ts"],"names":[],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Langfuse Exporter for Mastra AI Tracing\n *\n * This exporter sends tracing data to Langfuse for AI observability.\n * Root spans start traces in Langfuse.\n * LLM_GENERATION spans become Langfuse generations, all others become spans.\n */\n\nimport type { AITracingExporter, AITracingEvent, AnyAISpan, LLMGenerationAttributes } from '@mastra/core/ai-tracing';\nimport { AISpanType, omitKeys } from '@mastra/core/ai-tracing';\nimport { ConsoleLogger } from '@mastra/core/logger';\nimport { Langfuse } from 'langfuse';\nimport type { LangfuseTraceClient, LangfuseSpanClient, LangfuseGenerationClient, LangfuseEventClient } from 'langfuse';\n\nexport interface LangfuseExporterConfig {\n /** Langfuse API key */\n publicKey?: string;\n /** Langfuse secret key */\n secretKey?: string;\n /** Langfuse host URL */\n baseUrl?: string;\n /** Enable realtime mode - flushes after each event for immediate visibility */\n realtime?: boolean;\n /** Logger level for diagnostic messages (default: 'warn') */\n logLevel?: 'debug' | 'info' | 'warn' | 'error';\n /** Additional options to pass to the Langfuse client */\n options?: any;\n}\n\ntype TraceData = {\n trace: LangfuseTraceClient; // Langfuse trace object\n spans: Map<string, LangfuseSpanClient | LangfuseGenerationClient>; // Maps span.id to Langfuse span/generation\n events: Map<string, LangfuseEventClient>; // Maps span.id to Langfuse event\n};\n\ntype LangfuseParent = LangfuseTraceClient | LangfuseSpanClient | LangfuseGenerationClient | LangfuseEventClient;\n\nexport class LangfuseExporter implements AITracingExporter {\n name = 'langfuse';\n private client: Langfuse;\n private realtime: boolean;\n private traceMap = new Map<string, TraceData>();\n private logger: ConsoleLogger;\n\n constructor(config: LangfuseExporterConfig) {\n this.realtime = config.realtime ?? false;\n this.logger = new ConsoleLogger({ level: config.logLevel ?? 'warn' });\n\n if (!config.publicKey || !config.secretKey) {\n this.logger.error('LangfuseExporter: Missing required credentials, exporter will be disabled', {\n hasPublicKey: !!config.publicKey,\n hasSecretKey: !!config.secretKey,\n });\n // Create a no-op client to prevent runtime errors\n this.client = null as any;\n return;\n }\n\n this.client = new Langfuse({\n publicKey: config.publicKey,\n secretKey: config.secretKey,\n baseUrl: config.baseUrl,\n ...config.options,\n });\n }\n\n async exportEvent(event: AITracingEvent): Promise<void> {\n if (!this.client) {\n // Exporter is disabled due to missing credentials\n return;\n }\n\n if (event.span.isEvent) {\n await this.handleEventSpan(event.span);\n return;\n }\n\n switch (event.type) {\n case 'span_started':\n await this.handleSpanStarted(event.span);\n break;\n case 'span_updated':\n await this.handleSpanUpdateOrEnd(event.span, false);\n break;\n case 'span_ended':\n await this.handleSpanUpdateOrEnd(event.span, true);\n break;\n }\n\n // Flush immediately in realtime mode for instant visibility\n if (this.realtime) {\n await this.client.flushAsync();\n }\n }\n\n private async handleSpanStarted(span: AnyAISpan): Promise<void> {\n if (span.isRootSpan) {\n this.initTrace(span);\n }\n const method = 'handleSpanStarted';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseParent = this.getLangfuseParent({ traceData, span, method });\n if (!langfuseParent) {\n return;\n }\n\n const payload = this.buildSpanPayload(span, true);\n\n const langfuseSpan =\n span.type === AISpanType.LLM_GENERATION ? langfuseParent.generation(payload) : langfuseParent.span(payload);\n\n traceData.spans.set(span.id, langfuseSpan);\n }\n\n private async handleSpanUpdateOrEnd(span: AnyAISpan, isEnd: boolean): Promise<void> {\n const method = isEnd ? 'handleSpanEnd' : 'handleSpanUpdate';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseSpan = traceData.spans.get(span.id);\n if (!langfuseSpan) {\n this.logger.warn('Langfuse exporter: No Langfuse span found for span update/end', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n return;\n }\n\n // use update for both update & end, so that we can use the\n // end time we set when ending the span.\n langfuseSpan.update(this.buildSpanPayload(span, false));\n\n if (isEnd && span.isRootSpan) {\n traceData.trace.update({ output: span.output });\n this.traceMap.delete(span.traceId);\n }\n }\n\n private async handleEventSpan(span: AnyAISpan): Promise<void> {\n if (span.isRootSpan) {\n this.logger.debug('Langfuse exporter: Creating trace', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n method: 'handleEventSpan',\n });\n this.initTrace(span);\n }\n const method = 'handleEventSpan';\n\n const traceData = this.getTraceData({ span, method });\n if (!traceData) {\n return;\n }\n\n const langfuseParent = this.getLangfuseParent({ traceData, span, method });\n if (!langfuseParent) {\n return;\n }\n\n const payload = this.buildSpanPayload(span, true);\n\n const langfuseEvent = langfuseParent.event(payload);\n\n traceData.events.set(span.id, langfuseEvent);\n }\n\n private initTrace(span: AnyAISpan): void {\n const trace = this.client.trace(this.buildTracePayload(span));\n this.traceMap.set(span.traceId, { trace, spans: new Map(), events: new Map() });\n }\n\n private getTraceData(options: { span: AnyAISpan; method: string }): TraceData | undefined {\n const { span, method } = options;\n if (this.traceMap.has(span.traceId)) {\n return this.traceMap.get(span.traceId);\n }\n this.logger.warn('Langfuse exporter: No trace data found for span', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n }\n\n private getLangfuseParent(options: {\n traceData: TraceData;\n span: AnyAISpan;\n method: string;\n }): LangfuseParent | undefined {\n const { traceData, span, method } = options;\n\n const parentId = span.parent?.id;\n if (!parentId) {\n return traceData.trace;\n }\n if (traceData.spans.has(parentId)) {\n return traceData.spans.get(parentId);\n }\n if (traceData.events.has(parentId)) {\n return traceData.events.get(parentId);\n }\n this.logger.warn('Langfuse exporter: No parent data found for span', {\n traceId: span.traceId,\n spanId: span.id,\n spanName: span.name,\n spanType: span.type,\n isRootSpan: span.isRootSpan,\n parentSpanId: span.parent?.id,\n method,\n });\n }\n\n private buildTracePayload(span: AnyAISpan): Record<string, any> {\n const payload: Record<string, any> = {\n id: span.traceId,\n name: span.name,\n };\n\n const { userId, sessionId, ...remainingMetadata } = span.metadata ?? {};\n\n if (userId) payload.userId = userId;\n if (sessionId) payload.sessionId = sessionId;\n if (span.input) payload.input = span.input;\n\n payload.metadata = {\n spanType: span.type,\n ...span.attributes,\n ...remainingMetadata,\n };\n\n return payload;\n }\n\n private buildSpanPayload(span: AnyAISpan, isCreate: boolean): Record<string, any> {\n const payload: Record<string, any> = {};\n\n if (isCreate) {\n payload.id = span.id;\n payload.name = span.name;\n payload.startTime = span.startTime;\n if (span.input !== undefined) payload.input = span.input;\n }\n\n if (span.output !== undefined) payload.output = span.output;\n if (span.endTime !== undefined) payload.endTime = span.endTime;\n\n const attributes = (span.attributes ?? {}) as Record<string, any>;\n\n // Strip special fields from metadata if used in top-level keys\n const attributesToOmit: string[] = [];\n\n if (span.type === AISpanType.LLM_GENERATION) {\n const llmAttr = attributes as LLMGenerationAttributes;\n\n if (llmAttr.model !== undefined) {\n payload.model = llmAttr.model;\n attributesToOmit.push('model');\n }\n\n if (llmAttr.usage !== undefined) {\n payload.usage = llmAttr.usage;\n attributesToOmit.push('usage');\n }\n\n if (llmAttr.parameters !== undefined) {\n payload.modelParameters = llmAttr.parameters;\n attributesToOmit.push('parameters');\n }\n }\n\n payload.metadata = {\n spanType: span.type,\n ...omitKeys(attributes, attributesToOmit),\n ...span.metadata,\n };\n\n if (span.errorInfo) {\n payload.level = 'ERROR';\n payload.statusMessage = span.errorInfo.message;\n }\n\n return payload;\n }\n\n async shutdown(): Promise<void> {\n if (this.client) {\n await this.client.shutdownAsync();\n }\n this.traceMap.clear();\n }\n}\n"]}
|
package/package.json
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@mastra/langfuse",
|
|
3
|
+
"version": "0.0.0-add-libsql-changeset-20250910154739",
|
|
4
|
+
"description": "Langfuse observability provider for Mastra - includes AI tracing and future observability features",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "dist/index.js",
|
|
7
|
+
"types": "dist/index.d.ts",
|
|
8
|
+
"files": [
|
|
9
|
+
"dist",
|
|
10
|
+
"CHANGELOG.md"
|
|
11
|
+
],
|
|
12
|
+
"exports": {
|
|
13
|
+
".": {
|
|
14
|
+
"import": {
|
|
15
|
+
"types": "./dist/index.d.ts",
|
|
16
|
+
"default": "./dist/index.js"
|
|
17
|
+
},
|
|
18
|
+
"require": {
|
|
19
|
+
"types": "./dist/index.d.ts",
|
|
20
|
+
"default": "./dist/index.cjs"
|
|
21
|
+
}
|
|
22
|
+
},
|
|
23
|
+
"./package.json": "./package.json"
|
|
24
|
+
},
|
|
25
|
+
"license": "Apache-2.0",
|
|
26
|
+
"dependencies": {
|
|
27
|
+
"langfuse": "^3.38.4"
|
|
28
|
+
},
|
|
29
|
+
"devDependencies": {
|
|
30
|
+
"@microsoft/api-extractor": "^7.52.8",
|
|
31
|
+
"@types/node": "^20.19.0",
|
|
32
|
+
"eslint": "^9.30.1",
|
|
33
|
+
"tsup": "^8.5.0",
|
|
34
|
+
"typescript": "^5.8.3",
|
|
35
|
+
"vitest": "^3.2.4",
|
|
36
|
+
"@internal/lint": "0.0.0-add-libsql-changeset-20250910154739",
|
|
37
|
+
"@internal/types-builder": "0.0.0-add-libsql-changeset-20250910154739",
|
|
38
|
+
"@mastra/core": "0.0.0-add-libsql-changeset-20250910154739"
|
|
39
|
+
},
|
|
40
|
+
"peerDependencies": {
|
|
41
|
+
"@mastra/core": "0.0.0-add-libsql-changeset-20250910154739"
|
|
42
|
+
},
|
|
43
|
+
"homepage": "https://mastra.ai",
|
|
44
|
+
"repository": {
|
|
45
|
+
"type": "git",
|
|
46
|
+
"url": "git+https://github.com/mastra-ai/mastra.git",
|
|
47
|
+
"directory": "observability/langfuse"
|
|
48
|
+
},
|
|
49
|
+
"bugs": {
|
|
50
|
+
"url": "https://github.com/mastra-ai/mastra/issues"
|
|
51
|
+
},
|
|
52
|
+
"scripts": {
|
|
53
|
+
"build": "tsup --silent --config tsup.config.ts",
|
|
54
|
+
"build:watch": "pnpm build --watch",
|
|
55
|
+
"test": "vitest run",
|
|
56
|
+
"test:watch": "vitest watch",
|
|
57
|
+
"lint": "eslint ."
|
|
58
|
+
}
|
|
59
|
+
}
|