@introspection-sdk/introspection-node 0.4.6 → 0.4.7
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/.turbo/turbo-build.log +1 -1
- package/README.md +262 -0
- package/package.json +4 -4
package/.turbo/turbo-build.log
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
|
|
2
|
-
> @introspection-sdk/introspection-node@0.4.
|
|
2
|
+
> @introspection-sdk/introspection-node@0.4.7 build /home/runner/work/introspection-js-sdk/introspection-js-sdk/packages/introspection-node
|
|
3
3
|
> tsc
|
|
4
4
|
|
package/README.md
ADDED
|
@@ -0,0 +1,262 @@
|
|
|
1
|
+
# @introspection-sdk/introspection-node
|
|
2
|
+
|
|
3
|
+
Node.js SDK for [Introspection](https://introspection.dev) — API client, analytics events, and OpenTelemetry trace instrumentation.
|
|
4
|
+
|
|
5
|
+
## Install
|
|
6
|
+
|
|
7
|
+
```shell
|
|
8
|
+
pnpm add @introspection-sdk/introspection-node
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
For OTel features (analytics, traces, instrumentors), also install the peer dependencies:
|
|
12
|
+
|
|
13
|
+
```shell
|
|
14
|
+
pnpm add @opentelemetry/api @opentelemetry/api-logs \
|
|
15
|
+
@opentelemetry/sdk-trace-base @opentelemetry/sdk-trace-node \
|
|
16
|
+
@opentelemetry/sdk-logs @opentelemetry/exporter-trace-otlp-proto \
|
|
17
|
+
@opentelemetry/exporter-logs-otlp-proto @opentelemetry/resources \
|
|
18
|
+
@opentelemetry/semantic-conventions @opentelemetry/context-async-hooks \
|
|
19
|
+
@opentelemetry/core
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Introspection API (runtimes, tasks, files)
|
|
23
|
+
|
|
24
|
+
The main Introspection API surface. No OTel packages required.
|
|
25
|
+
|
|
26
|
+
```typescript
|
|
27
|
+
import { IntrospectionClient } from "@introspection-sdk/introspection-node";
|
|
28
|
+
|
|
29
|
+
const client = new IntrospectionClient();
|
|
30
|
+
|
|
31
|
+
const runner = await client.runtimes("customer-agent").run();
|
|
32
|
+
|
|
33
|
+
const run = await runner.tasks.start({
|
|
34
|
+
prompt: "Say hello in one sentence.",
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
for await (const event of run.stream()) {
|
|
38
|
+
console.log(`[${event.event}] ${event.data}`);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
await runner.close();
|
|
42
|
+
await client.shutdown();
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
## One-liner `introspection.init()`
|
|
46
|
+
|
|
47
|
+
`init()` auto-detects installed LLM frameworks (Anthropic, Gemini, OpenAI Agents, Vercel AI SDK, Claude Agent SDK, LangChain, Mastra, Pi) and wires them into a single shared trace pipeline:
|
|
48
|
+
|
|
49
|
+
```typescript
|
|
50
|
+
import * as introspection from "@introspection-sdk/introspection-node/otel";
|
|
51
|
+
import Anthropic from "@anthropic-ai/sdk";
|
|
52
|
+
|
|
53
|
+
await introspection.init({ serviceName: "my-app" });
|
|
54
|
+
|
|
55
|
+
const client = new Anthropic();
|
|
56
|
+
await introspection.conversation(() =>
|
|
57
|
+
client.messages.create({
|
|
58
|
+
model: "claude-sonnet-4-6",
|
|
59
|
+
max_tokens: 256,
|
|
60
|
+
messages: [{ role: "user", content: "Hello!" }],
|
|
61
|
+
}),
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
introspection.track("Signed up", { plan: "pro" });
|
|
65
|
+
await introspection.shutdown();
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
Both import styles work:
|
|
69
|
+
|
|
70
|
+
```typescript
|
|
71
|
+
import {
|
|
72
|
+
init,
|
|
73
|
+
conversation,
|
|
74
|
+
track,
|
|
75
|
+
} from "@introspection-sdk/introspection-node/otel";
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
### Dual export
|
|
79
|
+
|
|
80
|
+
Build the OpenTelemetry provider yourself with both span processors:
|
|
81
|
+
|
|
82
|
+
```typescript
|
|
83
|
+
import { NodeTracerProvider } from "@opentelemetry/sdk-trace-node";
|
|
84
|
+
import { BatchSpanProcessor } from "@opentelemetry/sdk-trace-base";
|
|
85
|
+
import { IntrospectionSpanProcessor } from "@introspection-sdk/introspection-node/otel";
|
|
86
|
+
|
|
87
|
+
const provider = new NodeTracerProvider({
|
|
88
|
+
spanProcessors: [
|
|
89
|
+
new IntrospectionSpanProcessor({ token: process.env.INTROSPECTION_TOKEN }),
|
|
90
|
+
new BatchSpanProcessor(langfuseExporter),
|
|
91
|
+
],
|
|
92
|
+
});
|
|
93
|
+
provider.register();
|
|
94
|
+
|
|
95
|
+
await introspection.init({ tracerProvider: provider });
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
`IntrospectionSpanProcessor` exports its own converted copy of each span, so the vendor processor receives the raw span and processor order is irrelevant. For a quick alternative: `init({ spanProcessors: [new BatchSpanProcessor(langfuseExporter)] })`.
|
|
99
|
+
|
|
100
|
+
Frameworks whose hooks are attached per-call (LangChain), per-config (Mastra), or per-instance (Pi, Claude Agent SDK) are bound by `init()` and exposed via accessors — `introspection.getLangchainHandler()`, `introspection.getMastraExporter()`, `introspection.instrumentPi(agent, meta)`, `introspection.instrumentClaudeAgent(sdk)`.
|
|
101
|
+
|
|
102
|
+
## Analytics events (track, feedback, identify)
|
|
103
|
+
|
|
104
|
+
```typescript
|
|
105
|
+
import { IntrospectionLogs } from "@introspection-sdk/introspection-node/otel";
|
|
106
|
+
|
|
107
|
+
const logs = new IntrospectionLogs({
|
|
108
|
+
token: process.env.INTROSPECTION_TOKEN,
|
|
109
|
+
serviceName: "my-service",
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
await logs.withUserId("user_123", async () => {
|
|
113
|
+
await logs.withConversation("conv_456", "msg_123", async () => {
|
|
114
|
+
logs.feedback("thumbs_up", { comments: "Great response!" });
|
|
115
|
+
});
|
|
116
|
+
});
|
|
117
|
+
|
|
118
|
+
logs.track("Button Clicked", { buttonId: "submit" });
|
|
119
|
+
logs.identify("user_123", { email: "user@example.com" });
|
|
120
|
+
|
|
121
|
+
await logs.shutdown();
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
### Methods
|
|
125
|
+
|
|
126
|
+
| Method | Description |
|
|
127
|
+
| --------------------------- | ------------------------------ |
|
|
128
|
+
| `track(event, properties?)` | Track any user action |
|
|
129
|
+
| `feedback(type, options?)` | Track feedback on AI responses |
|
|
130
|
+
| `identify(userId, traits?)` | Associate a user with traits |
|
|
131
|
+
| `flush()` | Flush pending events |
|
|
132
|
+
| `shutdown()` | Shutdown and flush |
|
|
133
|
+
|
|
134
|
+
### Context helpers (OTel baggage)
|
|
135
|
+
|
|
136
|
+
| Method | Description |
|
|
137
|
+
| ---------------------------------------------- | ---------------------------- |
|
|
138
|
+
| `withUserId(id, callback)` | Set user context |
|
|
139
|
+
| `withConversation(id?, responseId?, callback)` | Set conversation context |
|
|
140
|
+
| `withAgent(name, id?, callback)` | Set agent context |
|
|
141
|
+
| `withAnonymousId(id, callback)` | Set anonymous ID |
|
|
142
|
+
| `withBaggage(values, callback)` | Set arbitrary baggage values |
|
|
143
|
+
|
|
144
|
+
## Framework integrations
|
|
145
|
+
|
|
146
|
+
### OpenTelemetry Span Processor
|
|
147
|
+
|
|
148
|
+
```typescript
|
|
149
|
+
import { IntrospectionSpanProcessor } from "@introspection-sdk/introspection-node/otel";
|
|
150
|
+
import logfire from "@logfire/node";
|
|
151
|
+
|
|
152
|
+
logfire.configure({
|
|
153
|
+
additionalSpanProcessors: [
|
|
154
|
+
new IntrospectionSpanProcessor({ token: process.env.INTROSPECTION_TOKEN }),
|
|
155
|
+
],
|
|
156
|
+
});
|
|
157
|
+
|
|
158
|
+
logfire.instrumentOpenAI();
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
### OpenAI Agents SDK
|
|
162
|
+
|
|
163
|
+
```typescript
|
|
164
|
+
import { Agent, run, addTraceProcessor } from "@openai/agents";
|
|
165
|
+
import { IntrospectionTracingProcessor } from "@introspection-sdk/introspection-node/otel";
|
|
166
|
+
|
|
167
|
+
const processor = new IntrospectionTracingProcessor();
|
|
168
|
+
addTraceProcessor(processor);
|
|
169
|
+
|
|
170
|
+
const agent = new Agent({ name: "my-agent", model: "gpt-4o" });
|
|
171
|
+
const result = await run(agent, "Hello!");
|
|
172
|
+
|
|
173
|
+
await processor.shutdown();
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
### Claude Agent SDK
|
|
177
|
+
|
|
178
|
+
```typescript
|
|
179
|
+
import * as sdk from "@anthropic-ai/claude-agent-sdk";
|
|
180
|
+
import { withIntrospection } from "@introspection-sdk/introspection-node/otel";
|
|
181
|
+
|
|
182
|
+
const tracedSdk = withIntrospection(sdk);
|
|
183
|
+
const stream = tracedSdk.query({
|
|
184
|
+
prompt: "What is 2 + 2?",
|
|
185
|
+
options: { model: "claude-sonnet-4-5-20250929", maxTurns: 1 },
|
|
186
|
+
});
|
|
187
|
+
|
|
188
|
+
for await (const message of stream) {
|
|
189
|
+
/* ... */
|
|
190
|
+
}
|
|
191
|
+
await tracedSdk.shutdown();
|
|
192
|
+
```
|
|
193
|
+
|
|
194
|
+
### Vercel AI SDK
|
|
195
|
+
|
|
196
|
+
```typescript
|
|
197
|
+
import { setupTracing } from "@introspection-sdk/introspection-node/otel";
|
|
198
|
+
import { generateText } from "ai";
|
|
199
|
+
import { openai } from "@ai-sdk/openai";
|
|
200
|
+
|
|
201
|
+
const provider = setupTracing({ serviceName: "my-app" });
|
|
202
|
+
|
|
203
|
+
const { text } = await generateText({
|
|
204
|
+
model: openai("gpt-4o"),
|
|
205
|
+
prompt: "Hello!",
|
|
206
|
+
experimental_telemetry: { isEnabled: true },
|
|
207
|
+
});
|
|
208
|
+
|
|
209
|
+
await provider.shutdown();
|
|
210
|
+
```
|
|
211
|
+
|
|
212
|
+
### Mastra
|
|
213
|
+
|
|
214
|
+
```typescript
|
|
215
|
+
import { Mastra } from "@mastra/core/mastra";
|
|
216
|
+
import { IntrospectionMastraExporter } from "@introspection-sdk/introspection-node/mastra";
|
|
217
|
+
|
|
218
|
+
const mastra = new Mastra({
|
|
219
|
+
agents: { myAgent },
|
|
220
|
+
observability: {
|
|
221
|
+
configs: {
|
|
222
|
+
otel: {
|
|
223
|
+
serviceName: "my-mastra-app",
|
|
224
|
+
exporters: [new IntrospectionMastraExporter()],
|
|
225
|
+
},
|
|
226
|
+
},
|
|
227
|
+
},
|
|
228
|
+
});
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
### LangChain / LangGraph
|
|
232
|
+
|
|
233
|
+
```typescript
|
|
234
|
+
import { IntrospectionCallbackHandler } from "@introspection-sdk/introspection-node/langchain";
|
|
235
|
+
import { ChatOpenAI } from "@langchain/openai";
|
|
236
|
+
|
|
237
|
+
const handler = new IntrospectionCallbackHandler();
|
|
238
|
+
const model = new ChatOpenAI({ modelName: "gpt-4o" });
|
|
239
|
+
const response = await model.invoke("Hello!", { callbacks: [handler] });
|
|
240
|
+
|
|
241
|
+
await handler.shutdown();
|
|
242
|
+
```
|
|
243
|
+
|
|
244
|
+
For LangGraph, pass the app's session id as `thread_id`:
|
|
245
|
+
|
|
246
|
+
```typescript
|
|
247
|
+
await graph.invoke(input, {
|
|
248
|
+
callbacks: [handler],
|
|
249
|
+
configurable: { thread_id: "user-session-123" },
|
|
250
|
+
});
|
|
251
|
+
```
|
|
252
|
+
|
|
253
|
+
> See [examples/](../../examples/) for complete integration patterns including dual-export with Arize, Langfuse, Braintrust, and LangSmith.
|
|
254
|
+
|
|
255
|
+
## Environment variables
|
|
256
|
+
|
|
257
|
+
```shell
|
|
258
|
+
export INTROSPECTION_TOKEN="intro_xxx"
|
|
259
|
+
export INTROSPECTION_BASE_API_URL="https://api.introspection.dev" # optional
|
|
260
|
+
export INTROSPECTION_BASE_OTEL_URL="https://otel.introspection.dev" # optional
|
|
261
|
+
export INTROSPECTION_SERVICE_NAME="my-service" # optional
|
|
262
|
+
```
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@introspection-sdk/introspection-node",
|
|
3
|
-
"version": "0.4.
|
|
3
|
+
"version": "0.4.7",
|
|
4
4
|
"license": "Apache-2.0",
|
|
5
5
|
"description": "Introspection observability SDK for Node.js",
|
|
6
6
|
"engines": {
|
|
@@ -138,9 +138,9 @@
|
|
|
138
138
|
"dependencies": {
|
|
139
139
|
"@opentelemetry/api": "^1.9.1",
|
|
140
140
|
"https-proxy-agent": "^7.0.6",
|
|
141
|
-
"@introspection-sdk/introspection-pi": "0.4.
|
|
142
|
-
"@introspection-sdk/
|
|
143
|
-
"@introspection-sdk/
|
|
141
|
+
"@introspection-sdk/introspection-pi": "0.4.7",
|
|
142
|
+
"@introspection-sdk/introspection-proxy": "0.4.7",
|
|
143
|
+
"@introspection-sdk/types": "0.4.7"
|
|
144
144
|
},
|
|
145
145
|
"scripts": {
|
|
146
146
|
"lint": "eslint . --max-warnings 0",
|