@raindrop-ai/ai-sdk 0.0.30 → 0.0.32
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 +37 -0
- package/dist/{chunk-LM3XO4KR.mjs → chunk-YDMJ6ABM.mjs} +273 -164
- package/dist/{index-Ba_ZzUH4.d.mts → index-CwK0GdEe.d.mts} +46 -1
- package/dist/{index-Ba_ZzUH4.d.ts → index-CwK0GdEe.d.ts} +46 -1
- package/dist/index.browser.d.mts +46 -1
- package/dist/index.browser.d.ts +46 -1
- package/dist/index.browser.js +286 -177
- package/dist/index.browser.mjs +286 -177
- package/dist/index.node.d.mts +1 -1
- package/dist/index.node.d.ts +1 -1
- package/dist/index.node.js +286 -177
- package/dist/index.node.mjs +1 -1
- package/dist/index.workers.d.mts +1 -1
- package/dist/index.workers.d.ts +1 -1
- package/dist/index.workers.js +286 -177
- package/dist/index.workers.mjs +1 -1
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -136,6 +136,43 @@ registerTelemetry(
|
|
|
136
136
|
);
|
|
137
137
|
```
|
|
138
138
|
|
|
139
|
+
### Standalone self-diagnostics tool
|
|
140
|
+
|
|
141
|
+
When registering the native telemetry integration directly, create the
|
|
142
|
+
self-diagnostics tool from the same Raindrop client:
|
|
143
|
+
|
|
144
|
+
```ts
|
|
145
|
+
import { createRaindropAISDK } from "@raindrop-ai/ai-sdk";
|
|
146
|
+
import { generateText, registerTelemetry } from "ai";
|
|
147
|
+
|
|
148
|
+
const raindrop = createRaindropAISDK({
|
|
149
|
+
writeKey: process.env.RAINDROP_WRITE_KEY!,
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
registerTelemetry(raindrop.createTelemetryIntegration({ userId: "user_123" }));
|
|
153
|
+
|
|
154
|
+
const diagnostics = raindrop.createSelfDiagnosticsTool();
|
|
155
|
+
|
|
156
|
+
await generateText({
|
|
157
|
+
model,
|
|
158
|
+
prompt,
|
|
159
|
+
tools: {
|
|
160
|
+
[diagnostics.name]: diagnostics,
|
|
161
|
+
},
|
|
162
|
+
experimental_telemetry: { isEnabled: true },
|
|
163
|
+
});
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
With native telemetry and tracing enabled, the tool automatically attaches its
|
|
167
|
+
signal to the active Raindrop event. When there is no active trace context,
|
|
168
|
+
provide `eventId` or `getEventId`:
|
|
169
|
+
|
|
170
|
+
```ts
|
|
171
|
+
const diagnostics = raindrop.createSelfDiagnosticsTool({
|
|
172
|
+
getEventId: () => currentEventId,
|
|
173
|
+
});
|
|
174
|
+
```
|
|
175
|
+
|
|
139
176
|
Setting `nativeTelemetry: true` on pre-v7 throws a clear error. The Proxy path remains the default and supports features not yet available on the native path (`buildEvent`, output attachment extraction).
|
|
140
177
|
|
|
141
178
|
#### Per-call routing on AI SDK v7 beta.94+
|
|
@@ -2065,6 +2065,7 @@ var RaindropTelemetryIntegration = class {
|
|
|
2065
2065
|
attrInt("gen_ai.usage.output_tokens", usage.outputTokens)
|
|
2066
2066
|
);
|
|
2067
2067
|
}
|
|
2068
|
+
this.emitProviderExecutedToolSpans(event, state);
|
|
2068
2069
|
this.traceShipper.endSpan(state.stepSpan, { attributes: outputAttrs });
|
|
2069
2070
|
state.stepSpan = void 0;
|
|
2070
2071
|
state.stepParent = void 0;
|
|
@@ -2119,6 +2120,10 @@ var RaindropTelemetryIntegration = class {
|
|
|
2119
2120
|
this.traceShipper.endSpan(embedSpan, { attributes: outputAttrs });
|
|
2120
2121
|
state.embedSpans.delete(event.embedCallId);
|
|
2121
2122
|
};
|
|
2123
|
+
// v7 canary.159 renamed `onEmbedFinish` -> `onEmbedEnd`. Both names forward
|
|
2124
|
+
// to the same implementation; the installed SDK only wires up whichever it
|
|
2125
|
+
// knows about, so there is no double dispatch.
|
|
2126
|
+
this.onEmbedEnd = (event) => this.onEmbedFinish(event);
|
|
2122
2127
|
// ── onFinish ────────────────────────────────────────────────────────────
|
|
2123
2128
|
this.onFinish = (event) => {
|
|
2124
2129
|
const state = this.getState(event.callId);
|
|
@@ -2134,6 +2139,12 @@ var RaindropTelemetryIntegration = class {
|
|
|
2134
2139
|
}
|
|
2135
2140
|
this.cleanup(event.callId);
|
|
2136
2141
|
};
|
|
2142
|
+
// v7 < canary.159 dispatched `onFinish` as the operation finalizer; canary.159
|
|
2143
|
+
// renamed it to `onEnd` (the same change renamed onEmbedFinish -> onEmbedEnd
|
|
2144
|
+
// and onRerankFinish -> onRerankEnd). The event shape is unchanged, so this
|
|
2145
|
+
// is a thin alias to one implementation. The installed SDK wires up whichever
|
|
2146
|
+
// name it knows about, so old and new names never double dispatch.
|
|
2147
|
+
this.onEnd = (event) => this.onFinish(event);
|
|
2137
2148
|
// ── onError ─────────────────────────────────────────────────────────────
|
|
2138
2149
|
this.onError = (error) => {
|
|
2139
2150
|
var _a;
|
|
@@ -2331,6 +2342,74 @@ var RaindropTelemetryIntegration = class {
|
|
|
2331
2342
|
this.emitLive(state, "tool_result", event.toolCall.toolName);
|
|
2332
2343
|
state.toolSpans.delete(event.toolCall.toolCallId);
|
|
2333
2344
|
}
|
|
2345
|
+
// ── provider-executed tool calls ─────────────────────────────────────────
|
|
2346
|
+
//
|
|
2347
|
+
// Provider-executed (server-side) tools — e.g. Anthropic's hosted
|
|
2348
|
+
// `web_search` (`anthropic.web_search_20250305`) — are run by the provider,
|
|
2349
|
+
// not by the AI SDK. They therefore never flow through the client
|
|
2350
|
+
// `onToolExecutionStart`/`onToolExecutionEnd` callbacks that emit our
|
|
2351
|
+
// `ai.toolCall` spans; the SDK only surfaces them as `tool-call` /
|
|
2352
|
+
// `tool-result` content parts on the step (carrying `providerExecuted: true`).
|
|
2353
|
+
// Without this, such calls are invisible in every trace backend.
|
|
2354
|
+
//
|
|
2355
|
+
// At step finish we synthesize the same `ai.toolCall` span shape we emit for
|
|
2356
|
+
// client tools (name `ai.toolCall`, `operationId: "ai.toolCall"`, attrs
|
|
2357
|
+
// `ai.toolCall.name`/`id`/`args`/`result`), parented under the step span, so
|
|
2358
|
+
// downstream ingestion maps them to a tool span with no special-casing.
|
|
2359
|
+
//
|
|
2360
|
+
// Client-executed tools are excluded (`providerExecuted` falsy) — they were
|
|
2361
|
+
// already spanned during execution, so this never double-emits.
|
|
2362
|
+
emitProviderExecutedToolSpans(event, state) {
|
|
2363
|
+
if (!state.stepParent) return;
|
|
2364
|
+
const content = Array.isArray(event.content) ? event.content : [];
|
|
2365
|
+
const providerToolCalls = content.filter(
|
|
2366
|
+
(part) => (part == null ? void 0 : part.type) === "tool-call" && part.providerExecuted === true
|
|
2367
|
+
);
|
|
2368
|
+
if (providerToolCalls.length === 0) return;
|
|
2369
|
+
const resultsByCallId = /* @__PURE__ */ new Map();
|
|
2370
|
+
for (const part of content) {
|
|
2371
|
+
if (((part == null ? void 0 : part.type) === "tool-result" || (part == null ? void 0 : part.type) === "tool-error") && typeof part.toolCallId === "string") {
|
|
2372
|
+
resultsByCallId.set(part.toolCallId, part);
|
|
2373
|
+
}
|
|
2374
|
+
}
|
|
2375
|
+
for (const call of providerToolCalls) {
|
|
2376
|
+
const { operationName, resourceName } = opName(
|
|
2377
|
+
"ai.toolCall",
|
|
2378
|
+
state.functionId
|
|
2379
|
+
);
|
|
2380
|
+
const inputAttrs = state.recordInputs ? [attrString("ai.toolCall.args", safeJsonWithUint8(call.input))] : [];
|
|
2381
|
+
const toolSpan = this.traceShipper.startSpan({
|
|
2382
|
+
name: "ai.toolCall",
|
|
2383
|
+
parent: state.stepParent,
|
|
2384
|
+
eventId: state.eventId,
|
|
2385
|
+
operationId: "ai.toolCall",
|
|
2386
|
+
attributes: [
|
|
2387
|
+
attrString("operation.name", operationName),
|
|
2388
|
+
attrString("resource.name", resourceName),
|
|
2389
|
+
attrString("ai.telemetry.functionId", state.functionId),
|
|
2390
|
+
attrString("ai.toolCall.name", call.toolName),
|
|
2391
|
+
attrString("ai.toolCall.id", call.toolCallId),
|
|
2392
|
+
attrString("ai.toolCall.providerExecuted", "true"),
|
|
2393
|
+
...inputAttrs
|
|
2394
|
+
]
|
|
2395
|
+
});
|
|
2396
|
+
state.toolCallCount += 1;
|
|
2397
|
+
this.emitLive(state, "tool_start", call.toolName, { args: call.input });
|
|
2398
|
+
const resultPart = resultsByCallId.get(call.toolCallId);
|
|
2399
|
+
if ((resultPart == null ? void 0 : resultPart.type) === "tool-error") {
|
|
2400
|
+
this.traceShipper.endSpan(toolSpan, { error: resultPart.error });
|
|
2401
|
+
} else {
|
|
2402
|
+
const outputAttrs = state.recordOutputs && resultPart && "output" in resultPart ? [
|
|
2403
|
+
attrString(
|
|
2404
|
+
"ai.toolCall.result",
|
|
2405
|
+
safeJsonWithUint8(resultPart.output)
|
|
2406
|
+
)
|
|
2407
|
+
] : [];
|
|
2408
|
+
this.traceShipper.endSpan(toolSpan, { attributes: outputAttrs });
|
|
2409
|
+
}
|
|
2410
|
+
this.emitLive(state, "tool_result", call.toolName);
|
|
2411
|
+
}
|
|
2412
|
+
}
|
|
2334
2413
|
finishGenerate(event, state) {
|
|
2335
2414
|
var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n;
|
|
2336
2415
|
if (state.rootSpan) {
|
|
@@ -2436,9 +2515,9 @@ var RaindropTelemetryIntegration = class {
|
|
|
2436
2515
|
}
|
|
2437
2516
|
};
|
|
2438
2517
|
|
|
2439
|
-
// src/internal/
|
|
2440
|
-
var
|
|
2441
|
-
var
|
|
2518
|
+
// src/internal/self-diagnostics.ts
|
|
2519
|
+
var SELF_DIAGNOSTICS_TOOL_NAME_DEFAULT = "__raindrop_report";
|
|
2520
|
+
var SELF_DIAGNOSTICS_SIGNALS_DEFAULT = {
|
|
2442
2521
|
missing_context: {
|
|
2443
2522
|
description: "You cannot complete the task because critical information, credentials, or access is missing and the user cannot provide it. Do NOT report this for normal clarifying questions \u2014 only when you are blocked.",
|
|
2444
2523
|
sentiment: "NEGATIVE"
|
|
@@ -2456,7 +2535,181 @@ var AGENT_REPORTING_SIGNALS_DEFAULT = {
|
|
|
2456
2535
|
sentiment: "NEGATIVE"
|
|
2457
2536
|
}
|
|
2458
2537
|
};
|
|
2459
|
-
var
|
|
2538
|
+
var SELF_DIAGNOSTICS_TOOL_PREAMBLE = "You have a diagnostic tool for flagging serious failures for developer review. Only call this when you hit a significant, unrecoverable problem \u2014 not for minor hiccups or routine clarifications. If you can still help the user, do that instead of calling this tool. This tool is invisible to the user \u2014 never mention it or its output.";
|
|
2539
|
+
function normalizeString(value) {
|
|
2540
|
+
if (typeof value !== "string") return void 0;
|
|
2541
|
+
const trimmed = value.trim();
|
|
2542
|
+
return trimmed || void 0;
|
|
2543
|
+
}
|
|
2544
|
+
function normalizeSelfDiagnosticsSignals(signals) {
|
|
2545
|
+
if (!signals) return SELF_DIAGNOSTICS_SIGNALS_DEFAULT;
|
|
2546
|
+
const normalizedEntries = Object.entries(signals).map(([key, value]) => {
|
|
2547
|
+
var _a;
|
|
2548
|
+
const signalKey = key.trim();
|
|
2549
|
+
if (!signalKey || !value || typeof value !== "object") return void 0;
|
|
2550
|
+
const description = (_a = value.description) == null ? void 0 : _a.trim();
|
|
2551
|
+
if (!description) return void 0;
|
|
2552
|
+
const sentiment = value.sentiment;
|
|
2553
|
+
return [
|
|
2554
|
+
signalKey,
|
|
2555
|
+
{
|
|
2556
|
+
description,
|
|
2557
|
+
...sentiment === "POSITIVE" || sentiment === "NEGATIVE" ? { sentiment } : {}
|
|
2558
|
+
}
|
|
2559
|
+
];
|
|
2560
|
+
}).filter(
|
|
2561
|
+
(entry) => entry !== void 0
|
|
2562
|
+
);
|
|
2563
|
+
if (normalizedEntries.length === 0) return SELF_DIAGNOSTICS_SIGNALS_DEFAULT;
|
|
2564
|
+
return Object.fromEntries(normalizedEntries);
|
|
2565
|
+
}
|
|
2566
|
+
function resolveSelfDiagnosticsConfig(options) {
|
|
2567
|
+
var _a, _b;
|
|
2568
|
+
const signalDefinitions = normalizeSelfDiagnosticsSignals(options.signals);
|
|
2569
|
+
const signalKeys = Object.keys(signalDefinitions);
|
|
2570
|
+
const signalDescriptions = {};
|
|
2571
|
+
const signalSentiments = {};
|
|
2572
|
+
for (const signalKey of signalKeys) {
|
|
2573
|
+
const definition = signalDefinitions[signalKey];
|
|
2574
|
+
if (!definition) continue;
|
|
2575
|
+
signalDescriptions[signalKey] = definition.description;
|
|
2576
|
+
signalSentiments[signalKey] = definition.sentiment;
|
|
2577
|
+
}
|
|
2578
|
+
const customGuidance = ((_a = options.guidance) == null ? void 0 : _a.trim()) || "";
|
|
2579
|
+
const toolName = ((_b = options.toolName) == null ? void 0 : _b.trim()) || SELF_DIAGNOSTICS_TOOL_NAME_DEFAULT;
|
|
2580
|
+
const signalList = signalKeys.map((signalKey) => {
|
|
2581
|
+
const sentiment = signalSentiments[signalKey];
|
|
2582
|
+
const sentimentTag = sentiment ? ` [${sentiment.toLowerCase()}]` : "";
|
|
2583
|
+
return `- ${signalKey}: ${signalDescriptions[signalKey]}${sentimentTag}`;
|
|
2584
|
+
}).join("\n");
|
|
2585
|
+
const guidanceBlock = customGuidance ? `
|
|
2586
|
+
Additional guidance: ${customGuidance}
|
|
2587
|
+
` : "";
|
|
2588
|
+
const toolDescription = `${SELF_DIAGNOSTICS_TOOL_PREAMBLE}
|
|
2589
|
+
|
|
2590
|
+
When to call:
|
|
2591
|
+
- You are blocked from completing the task due to missing information or access that the user cannot provide.
|
|
2592
|
+
- A tool is persistently failing across multiple attempts, not just a single transient error.
|
|
2593
|
+
- The task requires a tool, permission, or capability you do not have.
|
|
2594
|
+
- You genuinely cannot deliver what the user asked for despite trying.
|
|
2595
|
+
|
|
2596
|
+
When NOT to call:
|
|
2597
|
+
- Normal clarifying questions or back-and-forth with the user.
|
|
2598
|
+
- A single tool error that you can recover from or retry.
|
|
2599
|
+
- You successfully completed the task, even if it was difficult.
|
|
2600
|
+
- Policy refusals or content filtering \u2014 those are working as intended.
|
|
2601
|
+
|
|
2602
|
+
Rules:
|
|
2603
|
+
1. Pick the single best category.
|
|
2604
|
+
2. Do not fabricate issues. Only report what is evident from the conversation.
|
|
2605
|
+
3. Err on the side of NOT calling this tool. When in doubt, help the user instead.
|
|
2606
|
+
${guidanceBlock}
|
|
2607
|
+
Categories:
|
|
2608
|
+
` + signalList;
|
|
2609
|
+
return {
|
|
2610
|
+
toolName,
|
|
2611
|
+
toolDescription,
|
|
2612
|
+
signalKeys,
|
|
2613
|
+
signalKeySet: new Set(signalKeys),
|
|
2614
|
+
signalDescriptions,
|
|
2615
|
+
signalSentiments
|
|
2616
|
+
};
|
|
2617
|
+
}
|
|
2618
|
+
function normalizeSelfDiagnosticsConfig(options) {
|
|
2619
|
+
if (!(options == null ? void 0 : options.enabled)) return void 0;
|
|
2620
|
+
return resolveSelfDiagnosticsConfig(options);
|
|
2621
|
+
}
|
|
2622
|
+
function asVercelSchema(inputSchema) {
|
|
2623
|
+
const validatorSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.validator");
|
|
2624
|
+
const schemaSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.schema");
|
|
2625
|
+
return {
|
|
2626
|
+
[schemaSymbol]: true,
|
|
2627
|
+
[validatorSymbol]: true,
|
|
2628
|
+
_type: void 0,
|
|
2629
|
+
jsonSchema: inputSchema,
|
|
2630
|
+
validate: (value) => ({ success: true, value })
|
|
2631
|
+
};
|
|
2632
|
+
}
|
|
2633
|
+
function resolveStandaloneEventId(options) {
|
|
2634
|
+
var _a, _b, _c, _d, _e, _f;
|
|
2635
|
+
return (_f = (_d = (_b = normalizeString((_a = options.getEventId) == null ? void 0 : _a.call(options))) != null ? _b : normalizeString(options.eventId)) != null ? _d : normalizeString((_c = getContextManager().getParentSpanIds()) == null ? void 0 : _c.eventId)) != null ? _f : normalizeString((_e = getCurrentRaindropCallMetadata()) == null ? void 0 : _e.eventId);
|
|
2636
|
+
}
|
|
2637
|
+
function createSelfDiagnosticsToolDefinition(args) {
|
|
2638
|
+
const { config, eventShipper, getEventId, aiSDKVersion, debug } = args;
|
|
2639
|
+
const inputJsonSchema = {
|
|
2640
|
+
type: "object",
|
|
2641
|
+
additionalProperties: false,
|
|
2642
|
+
properties: {
|
|
2643
|
+
category: {
|
|
2644
|
+
type: "string",
|
|
2645
|
+
enum: config.signalKeys,
|
|
2646
|
+
description: "The single best-matching category from the list above."
|
|
2647
|
+
},
|
|
2648
|
+
detail: {
|
|
2649
|
+
type: "string",
|
|
2650
|
+
description: "One sentence of factual context: what happened and why it matters. Do not include PII or secrets."
|
|
2651
|
+
}
|
|
2652
|
+
},
|
|
2653
|
+
required: ["category", "detail"]
|
|
2654
|
+
};
|
|
2655
|
+
const inputSchema = asVercelSchema(inputJsonSchema);
|
|
2656
|
+
const execute = async (rawInput) => {
|
|
2657
|
+
var _a, _b;
|
|
2658
|
+
const fallbackCategory = (_a = config.signalKeys[0]) != null ? _a : "unknown";
|
|
2659
|
+
const categoryCandidate = normalizeString(rawInput == null ? void 0 : rawInput.category);
|
|
2660
|
+
const category = categoryCandidate && config.signalKeySet.has(categoryCandidate) ? categoryCandidate : fallbackCategory;
|
|
2661
|
+
const detail = normalizeString(rawInput == null ? void 0 : rawInput.detail);
|
|
2662
|
+
const eventId = getEventId();
|
|
2663
|
+
if (!eventId) {
|
|
2664
|
+
const message = "self diagnostics signal skipped: missing eventId. Pass eventId or getEventId when creating the tool.";
|
|
2665
|
+
if (args.onMissingEventId === "throw") {
|
|
2666
|
+
throw new Error(`[raindrop-ai/ai-sdk] ${message}`);
|
|
2667
|
+
}
|
|
2668
|
+
if (((_b = args.onMissingEventId) != null ? _b : "warn") === "warn") {
|
|
2669
|
+
console.warn(`[raindrop-ai/ai-sdk] ${message}`);
|
|
2670
|
+
}
|
|
2671
|
+
return { acknowledged: false, category, reason: "missing_event_id" };
|
|
2672
|
+
}
|
|
2673
|
+
void eventShipper.trackSignal({
|
|
2674
|
+
eventId,
|
|
2675
|
+
name: `self diagnostics - ${category}`,
|
|
2676
|
+
type: "agent",
|
|
2677
|
+
sentiment: config.signalSentiments[category],
|
|
2678
|
+
properties: {
|
|
2679
|
+
source: "agent_reporting_tool",
|
|
2680
|
+
category,
|
|
2681
|
+
signal_description: config.signalDescriptions[category],
|
|
2682
|
+
...aiSDKVersion ? { ai_sdk_version: aiSDKVersion } : {},
|
|
2683
|
+
...detail ? { detail } : {}
|
|
2684
|
+
}
|
|
2685
|
+
}).catch((error) => {
|
|
2686
|
+
if (debug) {
|
|
2687
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
2688
|
+
console.warn(`[raindrop-ai/ai-sdk] selfDiagnostics signal dispatch failed: ${message}`);
|
|
2689
|
+
}
|
|
2690
|
+
});
|
|
2691
|
+
return { acknowledged: true, category };
|
|
2692
|
+
};
|
|
2693
|
+
return {
|
|
2694
|
+
name: config.toolName,
|
|
2695
|
+
description: config.toolDescription,
|
|
2696
|
+
parameters: inputSchema,
|
|
2697
|
+
inputSchema,
|
|
2698
|
+
execute
|
|
2699
|
+
};
|
|
2700
|
+
}
|
|
2701
|
+
function createStandaloneSelfDiagnosticsTool(args) {
|
|
2702
|
+
const config = resolveSelfDiagnosticsConfig(args.options);
|
|
2703
|
+
return createSelfDiagnosticsToolDefinition({
|
|
2704
|
+
config,
|
|
2705
|
+
eventShipper: args.eventShipper,
|
|
2706
|
+
getEventId: () => resolveStandaloneEventId(args.options),
|
|
2707
|
+
onMissingEventId: args.options.onMissingEventId,
|
|
2708
|
+
debug: args.debug
|
|
2709
|
+
});
|
|
2710
|
+
}
|
|
2711
|
+
|
|
2712
|
+
// src/internal/wrap/wrapAISDK.ts
|
|
2460
2713
|
var pendingStoresByShipper = /* @__PURE__ */ new WeakMap();
|
|
2461
2714
|
var PendingToolSpanStore = class _PendingToolSpanStore {
|
|
2462
2715
|
constructor() {
|
|
@@ -2560,85 +2813,6 @@ function mergeContexts(wrapTime, callTime) {
|
|
|
2560
2813
|
}
|
|
2561
2814
|
return result;
|
|
2562
2815
|
}
|
|
2563
|
-
function normalizeSelfDiagnosticsSignals(signals) {
|
|
2564
|
-
if (!signals) return AGENT_REPORTING_SIGNALS_DEFAULT;
|
|
2565
|
-
const normalizedEntries = Object.entries(signals).map(([key, value]) => {
|
|
2566
|
-
var _a;
|
|
2567
|
-
const signalKey = key.trim();
|
|
2568
|
-
if (!signalKey || !value || typeof value !== "object") return void 0;
|
|
2569
|
-
const description = (_a = value.description) == null ? void 0 : _a.trim();
|
|
2570
|
-
if (!description) return void 0;
|
|
2571
|
-
const sentiment = value.sentiment;
|
|
2572
|
-
return [
|
|
2573
|
-
signalKey,
|
|
2574
|
-
{
|
|
2575
|
-
description,
|
|
2576
|
-
...sentiment === "POSITIVE" || sentiment === "NEGATIVE" ? { sentiment } : {}
|
|
2577
|
-
}
|
|
2578
|
-
];
|
|
2579
|
-
}).filter(
|
|
2580
|
-
(entry) => entry !== void 0
|
|
2581
|
-
);
|
|
2582
|
-
if (normalizedEntries.length === 0) return AGENT_REPORTING_SIGNALS_DEFAULT;
|
|
2583
|
-
return Object.fromEntries(normalizedEntries);
|
|
2584
|
-
}
|
|
2585
|
-
function normalizeSelfDiagnosticsConfig(options) {
|
|
2586
|
-
var _a, _b;
|
|
2587
|
-
if (!(options == null ? void 0 : options.enabled)) return void 0;
|
|
2588
|
-
const signalDefinitions = normalizeSelfDiagnosticsSignals(options.signals);
|
|
2589
|
-
const signalKeys = Object.keys(signalDefinitions);
|
|
2590
|
-
const signalDescriptions = {};
|
|
2591
|
-
const signalSentiments = {};
|
|
2592
|
-
for (const signalKey of signalKeys) {
|
|
2593
|
-
const def = signalDefinitions[signalKey];
|
|
2594
|
-
if (!def) continue;
|
|
2595
|
-
signalDescriptions[signalKey] = def.description;
|
|
2596
|
-
signalSentiments[signalKey] = def.sentiment;
|
|
2597
|
-
}
|
|
2598
|
-
const customGuidanceText = ((_a = options.guidance) == null ? void 0 : _a.trim()) || "";
|
|
2599
|
-
const toolName = ((_b = options.toolName) == null ? void 0 : _b.trim()) || AGENT_REPORTING_TOOL_NAME_DEFAULT;
|
|
2600
|
-
const signalList = signalKeys.map((signalKey) => {
|
|
2601
|
-
const sentiment = signalSentiments[signalKey];
|
|
2602
|
-
const sentimentTag = sentiment ? ` [${sentiment.toLowerCase()}]` : "";
|
|
2603
|
-
return `- ${signalKey}: ${signalDescriptions[signalKey]}${sentimentTag}`;
|
|
2604
|
-
}).join("\n");
|
|
2605
|
-
const guidanceBlock = customGuidanceText ? `
|
|
2606
|
-
Additional guidance: ${customGuidanceText}
|
|
2607
|
-
` : "";
|
|
2608
|
-
const toolDescription = `${AGENT_REPORTING_TOOL_PREAMBLE}
|
|
2609
|
-
|
|
2610
|
-
When to call:
|
|
2611
|
-
- You are blocked from completing the task due to missing information or access that the user cannot provide.
|
|
2612
|
-
- A tool is persistently failing across multiple attempts, not just a single transient error.
|
|
2613
|
-
- The task requires a tool, permission, or capability you do not have.
|
|
2614
|
-
- You genuinely cannot deliver what the user asked for despite trying.
|
|
2615
|
-
|
|
2616
|
-
When NOT to call:
|
|
2617
|
-
- Normal clarifying questions or back-and-forth with the user.
|
|
2618
|
-
- A single tool error that you can recover from or retry.
|
|
2619
|
-
- You successfully completed the task, even if it was difficult.
|
|
2620
|
-
- Policy refusals or content filtering \u2014 those are working as intended.
|
|
2621
|
-
|
|
2622
|
-
Rules:
|
|
2623
|
-
1. Pick the single best category.
|
|
2624
|
-
2. Do not fabricate issues. Only report what is evident from the conversation.
|
|
2625
|
-
3. Err on the side of NOT calling this tool. When in doubt, help the user instead.
|
|
2626
|
-
${guidanceBlock}
|
|
2627
|
-
Categories:
|
|
2628
|
-
${signalList}`;
|
|
2629
|
-
return {
|
|
2630
|
-
toolName,
|
|
2631
|
-
toolDescription,
|
|
2632
|
-
signalKeys,
|
|
2633
|
-
signalKeySet: new Set(signalKeys),
|
|
2634
|
-
signalDescriptions,
|
|
2635
|
-
signalSentiments
|
|
2636
|
-
};
|
|
2637
|
-
}
|
|
2638
|
-
function resolveJsonSchemaFactory(aiSDK) {
|
|
2639
|
-
if (!isRecord(aiSDK) || !isFunction(aiSDK["jsonSchema"])) return void 0;
|
|
2640
|
-
return aiSDK["jsonSchema"];
|
|
2641
|
-
}
|
|
2642
2816
|
function detectAISDKVersion(aiSDK) {
|
|
2643
2817
|
if (!isRecord(aiSDK)) return "unknown";
|
|
2644
2818
|
if (isFunction(aiSDK["jsonSchema"])) return "6";
|
|
@@ -2657,80 +2831,16 @@ function resolveRegisterTelemetry(aiSDK) {
|
|
|
2657
2831
|
const fn = (_a = aiSDK["registerTelemetry"]) != null ? _a : aiSDK["registerTelemetryIntegration"];
|
|
2658
2832
|
return isFunction(fn) ? fn : void 0;
|
|
2659
2833
|
}
|
|
2660
|
-
function asVercelSchema(jsonSchemaObj) {
|
|
2661
|
-
const validatorSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.validator");
|
|
2662
|
-
const schemaSymbol = /* @__PURE__ */ Symbol.for("vercel.ai.schema");
|
|
2663
|
-
return {
|
|
2664
|
-
[schemaSymbol]: true,
|
|
2665
|
-
[validatorSymbol]: true,
|
|
2666
|
-
_type: void 0,
|
|
2667
|
-
jsonSchema: jsonSchemaObj,
|
|
2668
|
-
validate: (value) => ({ success: true, value })
|
|
2669
|
-
};
|
|
2670
|
-
}
|
|
2671
2834
|
function createSelfDiagnosticsTool(ctx) {
|
|
2672
2835
|
const config = ctx.selfDiagnostics;
|
|
2673
2836
|
if (!config) return void 0;
|
|
2674
|
-
|
|
2675
|
-
|
|
2676
|
-
|
|
2677
|
-
|
|
2678
|
-
|
|
2679
|
-
|
|
2680
|
-
|
|
2681
|
-
description: "The single best-matching category from the list above."
|
|
2682
|
-
},
|
|
2683
|
-
detail: {
|
|
2684
|
-
type: "string",
|
|
2685
|
-
description: "One sentence of factual context: what happened and why it matters. Do not include PII or secrets."
|
|
2686
|
-
}
|
|
2687
|
-
},
|
|
2688
|
-
required: ["category", "detail"]
|
|
2689
|
-
};
|
|
2690
|
-
const parameters = asVercelSchema(schema);
|
|
2691
|
-
let inputSchema = parameters;
|
|
2692
|
-
if (ctx.jsonSchemaFactory) {
|
|
2693
|
-
try {
|
|
2694
|
-
inputSchema = ctx.jsonSchemaFactory(schema);
|
|
2695
|
-
} catch (e) {
|
|
2696
|
-
inputSchema = parameters;
|
|
2697
|
-
}
|
|
2698
|
-
}
|
|
2699
|
-
const execute = async (rawInput) => {
|
|
2700
|
-
var _a;
|
|
2701
|
-
const input = isRecord(rawInput) ? rawInput : void 0;
|
|
2702
|
-
const fallbackCategory = (_a = config.signalKeys[0]) != null ? _a : "unknown";
|
|
2703
|
-
const categoryCandidate = typeof (input == null ? void 0 : input["category"]) === "string" ? input["category"].trim() : void 0;
|
|
2704
|
-
const category = categoryCandidate && config.signalKeySet.has(categoryCandidate) ? categoryCandidate : fallbackCategory;
|
|
2705
|
-
const detail = typeof (input == null ? void 0 : input["detail"]) === "string" ? input["detail"].trim() : "";
|
|
2706
|
-
const signalDescription = config.signalDescriptions[category];
|
|
2707
|
-
const signalSentiment = config.signalSentiments[category];
|
|
2708
|
-
void ctx.eventShipper.trackSignal({
|
|
2709
|
-
eventId: ctx.eventId,
|
|
2710
|
-
name: `self diagnostics - ${category}`,
|
|
2711
|
-
type: "agent",
|
|
2712
|
-
sentiment: signalSentiment,
|
|
2713
|
-
properties: {
|
|
2714
|
-
source: "agent_reporting_tool",
|
|
2715
|
-
category,
|
|
2716
|
-
signal_description: signalDescription,
|
|
2717
|
-
ai_sdk_version: ctx.aiSDKVersion,
|
|
2718
|
-
...detail ? { detail } : {}
|
|
2719
|
-
}
|
|
2720
|
-
}).catch((err) => {
|
|
2721
|
-
if (ctx.debug) {
|
|
2722
|
-
const msg = err instanceof Error ? err.message : String(err);
|
|
2723
|
-
console.warn(`[raindrop-ai/ai-sdk] selfDiagnostics signal dispatch failed: ${msg}`);
|
|
2724
|
-
}
|
|
2725
|
-
});
|
|
2726
|
-
return { acknowledged: true, category };
|
|
2727
|
-
};
|
|
2728
|
-
return {
|
|
2729
|
-
description: config.toolDescription,
|
|
2730
|
-
execute,
|
|
2731
|
-
parameters,
|
|
2732
|
-
inputSchema
|
|
2733
|
-
};
|
|
2837
|
+
return createSelfDiagnosticsToolDefinition({
|
|
2838
|
+
config,
|
|
2839
|
+
eventShipper: ctx.eventShipper,
|
|
2840
|
+
getEventId: () => ctx.eventId,
|
|
2841
|
+
aiSDKVersion: ctx.aiSDKVersion,
|
|
2842
|
+
debug: ctx.debug
|
|
2843
|
+
});
|
|
2734
2844
|
}
|
|
2735
2845
|
function getCurrentParentSpanContextSync() {
|
|
2736
2846
|
return getContextManager().getParentSpanIds();
|
|
@@ -2957,7 +3067,6 @@ function setupOperation(params) {
|
|
|
2957
3067
|
eventShipper,
|
|
2958
3068
|
traceShipper,
|
|
2959
3069
|
rootParentForChildren,
|
|
2960
|
-
jsonSchemaFactory: resolveJsonSchemaFactory(aiSDK),
|
|
2961
3070
|
selfDiagnostics: operationSelfDiagnostics,
|
|
2962
3071
|
aiSDKVersion: detectAISDKVersion(aiSDK)
|
|
2963
3072
|
};
|
|
@@ -3306,7 +3415,6 @@ function wrapAISDK(aiSDK, deps) {
|
|
|
3306
3415
|
);
|
|
3307
3416
|
}
|
|
3308
3417
|
const selfDiagnostics2 = normalizeSelfDiagnosticsConfig(deps.options.selfDiagnostics);
|
|
3309
|
-
const jsonSchemaFactory = selfDiagnostics2 ? resolveJsonSchemaFactory(aiSDK) : void 0;
|
|
3310
3418
|
const metadataAwareOps = /* @__PURE__ */ new Set([
|
|
3311
3419
|
"generateText",
|
|
3312
3420
|
"streamText",
|
|
@@ -3338,14 +3446,9 @@ function wrapAISDK(aiSDK, deps) {
|
|
|
3338
3446
|
const perCallEventIdGenerated = !perCallEventIdExplicit;
|
|
3339
3447
|
const perCallCtx = {
|
|
3340
3448
|
eventId: perCallEventId,
|
|
3341
|
-
context: wrapTimeCtx,
|
|
3342
|
-
telemetry,
|
|
3343
|
-
sendTraces: false,
|
|
3344
3449
|
debug,
|
|
3345
3450
|
eventShipper: deps.eventShipper,
|
|
3346
3451
|
traceShipper: deps.traceShipper,
|
|
3347
|
-
rootParentForChildren: void 0,
|
|
3348
|
-
jsonSchemaFactory,
|
|
3349
3452
|
selfDiagnostics: selfDiagnostics2,
|
|
3350
3453
|
aiSDKVersion: "7"
|
|
3351
3454
|
};
|
|
@@ -3547,7 +3650,6 @@ function wrapAgentGenerate(generate, instance, agentSettings, className, aiSDK,
|
|
|
3547
3650
|
eventShipper: deps.eventShipper,
|
|
3548
3651
|
traceShipper: deps.traceShipper,
|
|
3549
3652
|
rootParentForChildren,
|
|
3550
|
-
jsonSchemaFactory: resolveJsonSchemaFactory(aiSDK),
|
|
3551
3653
|
selfDiagnostics,
|
|
3552
3654
|
aiSDKVersion: detectAISDKVersion(aiSDK)
|
|
3553
3655
|
};
|
|
@@ -3755,7 +3857,6 @@ function wrapAgentStream(stream, instance, agentSettings, className, aiSDK, deps
|
|
|
3755
3857
|
eventShipper: deps.eventShipper,
|
|
3756
3858
|
traceShipper: deps.traceShipper,
|
|
3757
3859
|
rootParentForChildren,
|
|
3758
|
-
jsonSchemaFactory: resolveJsonSchemaFactory(aiSDK),
|
|
3759
3860
|
selfDiagnostics,
|
|
3760
3861
|
aiSDKVersion: detectAISDKVersion(aiSDK)
|
|
3761
3862
|
};
|
|
@@ -4474,7 +4575,7 @@ function extractNestedTokens(usage, key) {
|
|
|
4474
4575
|
// package.json
|
|
4475
4576
|
var package_default = {
|
|
4476
4577
|
name: "@raindrop-ai/ai-sdk",
|
|
4477
|
-
version: "0.0.
|
|
4578
|
+
version: "0.0.32"};
|
|
4478
4579
|
|
|
4479
4580
|
// src/internal/version.ts
|
|
4480
4581
|
var libraryName = package_default.name;
|
|
@@ -4606,6 +4707,14 @@ function createRaindropAISDK(opts) {
|
|
|
4606
4707
|
traceShipper
|
|
4607
4708
|
});
|
|
4608
4709
|
},
|
|
4710
|
+
createSelfDiagnosticsTool(options = {}) {
|
|
4711
|
+
var _a2;
|
|
4712
|
+
return createStandaloneSelfDiagnosticsTool({
|
|
4713
|
+
options,
|
|
4714
|
+
eventShipper,
|
|
4715
|
+
debug: ((_a2 = opts.events) == null ? void 0 : _a2.debug) === true || envDebug
|
|
4716
|
+
});
|
|
4717
|
+
},
|
|
4609
4718
|
createTelemetryIntegration(contextOrOptions) {
|
|
4610
4719
|
const FLAT_CONTEXT_KEYS = [
|
|
4611
4720
|
"userId",
|
|
@@ -378,7 +378,9 @@ interface TelemetryIntegration {
|
|
|
378
378
|
onStepFinish?: Listener<any>;
|
|
379
379
|
onEmbedStart?: Listener<any>;
|
|
380
380
|
onEmbedFinish?: Listener<any>;
|
|
381
|
+
onEmbedEnd?: Listener<any>;
|
|
381
382
|
onFinish?: Listener<any>;
|
|
383
|
+
onEnd?: Listener<any>;
|
|
382
384
|
onError?: Listener<any>;
|
|
383
385
|
executeTool?: <T>(params: {
|
|
384
386
|
callId: string;
|
|
@@ -460,10 +462,13 @@ declare class RaindropTelemetryIntegration implements TelemetryIntegration {
|
|
|
460
462
|
onLanguageModelCallStart: (_event: any) => void;
|
|
461
463
|
onLanguageModelCallEnd: (_event: any) => void;
|
|
462
464
|
onChunk: (event: any) => void;
|
|
465
|
+
private emitProviderExecutedToolSpans;
|
|
463
466
|
onStepFinish: (event: any) => void;
|
|
464
467
|
onEmbedStart: (event: any) => void;
|
|
465
468
|
onEmbedFinish: (event: any) => void;
|
|
469
|
+
onEmbedEnd: (event: any) => void;
|
|
466
470
|
onFinish: (event: any) => void;
|
|
471
|
+
onEnd: (event: any) => void;
|
|
467
472
|
private finishGenerate;
|
|
468
473
|
private finishEmbed;
|
|
469
474
|
onError: (error: unknown) => void;
|
|
@@ -889,6 +894,38 @@ type SelfDiagnosticsOptions = {
|
|
|
889
894
|
*/
|
|
890
895
|
toolName?: string;
|
|
891
896
|
};
|
|
897
|
+
type SelfDiagnosticsToolOptions = Omit<SelfDiagnosticsOptions, "enabled"> & {
|
|
898
|
+
/** Fixed Raindrop event ID to attach diagnostic signals to. */
|
|
899
|
+
eventId?: string;
|
|
900
|
+
/** Dynamic event ID resolver, useful when one tool instance serves many runs. */
|
|
901
|
+
getEventId?: () => string | undefined;
|
|
902
|
+
/** Behavior when no event ID can be resolved. Default: "warn" */
|
|
903
|
+
onMissingEventId?: "warn" | "ignore" | "throw";
|
|
904
|
+
};
|
|
905
|
+
type SelfDiagnosticsToolInput = {
|
|
906
|
+
category: string;
|
|
907
|
+
detail: string;
|
|
908
|
+
};
|
|
909
|
+
type SelfDiagnosticsToolResult = {
|
|
910
|
+
acknowledged: true;
|
|
911
|
+
category: string;
|
|
912
|
+
} | {
|
|
913
|
+
acknowledged: false;
|
|
914
|
+
category: string;
|
|
915
|
+
reason: "missing_event_id";
|
|
916
|
+
};
|
|
917
|
+
type SelfDiagnosticsTool = {
|
|
918
|
+
name: string;
|
|
919
|
+
description: string;
|
|
920
|
+
/**
|
|
921
|
+
* AI SDK v4 tool schema. This is the same cross-version schema object as
|
|
922
|
+
* `inputSchema`; both fields are exposed so the tool works on AI SDK v4-v7.
|
|
923
|
+
*/
|
|
924
|
+
parameters: any;
|
|
925
|
+
/** AI SDK v5+ tool schema. */
|
|
926
|
+
inputSchema: any;
|
|
927
|
+
execute(input: SelfDiagnosticsToolInput): Promise<SelfDiagnosticsToolResult>;
|
|
928
|
+
};
|
|
892
929
|
type WrapAISDKOptions = {
|
|
893
930
|
context: RaindropAISDKContext | ((info: {
|
|
894
931
|
operation: string;
|
|
@@ -973,6 +1010,14 @@ type EventPatch = {
|
|
|
973
1010
|
};
|
|
974
1011
|
type RaindropAISDKClient = {
|
|
975
1012
|
wrap<T extends object>(aiSDK: T, options?: WrapAISDKOptions): WrappedAISDK<T>;
|
|
1013
|
+
/**
|
|
1014
|
+
* Create a standalone AI SDK self-diagnostics tool.
|
|
1015
|
+
*
|
|
1016
|
+
* The tool automatically uses the active Raindrop event while executing
|
|
1017
|
+
* under `createTelemetryIntegration()` with tracing enabled. Pass `eventId`
|
|
1018
|
+
* or `getEventId` when no active trace context is available.
|
|
1019
|
+
*/
|
|
1020
|
+
createSelfDiagnosticsTool(options?: SelfDiagnosticsToolOptions): SelfDiagnosticsTool;
|
|
976
1021
|
/**
|
|
977
1022
|
* Create a TelemetryIntegration instance for direct registration with AI SDK v7+.
|
|
978
1023
|
* Use with `registerTelemetryIntegration()` from the `ai` package.
|
|
@@ -1058,4 +1103,4 @@ type RaindropAISDKClient = {
|
|
|
1058
1103
|
};
|
|
1059
1104
|
declare function createRaindropAISDK(opts: RaindropAISDKOptions): RaindropAISDKClient;
|
|
1060
1105
|
|
|
1061
|
-
export {
|
|
1106
|
+
export { redactJsonAttributeValue as $, type AISDKChatRequestLike as A, type BuildEventPatch as B, ContextManager as C, DEFAULT_REDACT_ATTRIBUTE_KEYS as D, type EndSpanArgs as E, type WrappedAISDK as F, _resetRaindropCallMetadataStorage as G, _resetWarnedMissingUserId as H, type IdentifyInput as I, clearParentToolContext as J, createRaindropAISDK as K, currentSpan as L, defaultTransformSpan as M, enterParentToolContext as N, type OtlpAnyValue as O, type ParentToolContext as P, eventMetadata as Q, REDACTED_PLACEHOLDER as R, type SelfDiagnosticsOptions as S, type TraceSpan as T, eventMetadataFromChatRequest as U, getContextManager as V, type WrapAISDKOptions as W, getCurrentParentToolContext as X, getCurrentRaindropCallMetadata as Y, readRaindropCallMetadataFromArgs as Z, _resetParentToolContextStorage as _, type AISDKChatRequestMessageLike as a, redactSecretsInObject as a0, runWithParentToolContext as a1, runWithRaindropCallMetadata as a2, withCurrent as a3, type AISDKMessage as b, type AgentCallMetadata as c, type AgentWithMetadata as d, type Attachment as e, type ContextSpan as f, type CreateSpanArgs as g, DEFAULT_SECRET_KEY_NAMES as h, type EventBuilder as i, type EventMetadataOptions as j, type OtlpSpan as k, type RaindropAISDKClient as l, type RaindropAISDKContext as m, type RaindropAISDKOptions as n, type RaindropCallMetadata as o, RaindropTelemetryIntegration as p, type RaindropTelemetryIntegrationOptions as q, type SelfDiagnosticsSignalDefinition as r, type SelfDiagnosticsSignalDefinitions as s, type SelfDiagnosticsTool as t, type SelfDiagnosticsToolInput as u, type SelfDiagnosticsToolOptions as v, type SelfDiagnosticsToolResult as w, type StartSpanArgs as x, type TransformSpanHook as y, type WrappedAI as z };
|