@mgvdev/nestjs-ai 0.1.0
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/LICENSE +21 -0
- package/README.md +655 -0
- package/dist/ai-module-options.interface-B5X4AFLC.d.cts +192 -0
- package/dist/ai-module-options.interface-Ca6y_MY2.d.ts +192 -0
- package/dist/conversation-store.interface-CtQY-qcc.d.cts +30 -0
- package/dist/conversation-store.interface-CtQY-qcc.d.ts +30 -0
- package/dist/index.cjs +3209 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +1441 -0
- package/dist/index.d.ts +1441 -0
- package/dist/index.js +3163 -0
- package/dist/index.js.map +1 -0
- package/dist/stream-to-socket-fJphU0WN.d.cts +47 -0
- package/dist/stream-to-socket-fJphU0WN.d.ts +47 -0
- package/dist/testing.cjs +2395 -0
- package/dist/testing.cjs.map +1 -0
- package/dist/testing.d.cts +46 -0
- package/dist/testing.d.ts +46 -0
- package/dist/testing.js +2391 -0
- package/dist/testing.js.map +1 -0
- package/dist/typeorm.cjs +115 -0
- package/dist/typeorm.cjs.map +1 -0
- package/dist/typeorm.d.cts +44 -0
- package/dist/typeorm.d.ts +44 -0
- package/dist/typeorm.js +113 -0
- package/dist/typeorm.js.map +1 -0
- package/dist/websocket.cjs +154 -0
- package/dist/websocket.cjs.map +1 -0
- package/dist/websocket.d.cts +25 -0
- package/dist/websocket.d.ts +25 -0
- package/dist/websocket.js +152 -0
- package/dist/websocket.js.map +1 -0
- package/documentation/README.md +44 -0
- package/documentation/agents-and-tools.md +102 -0
- package/documentation/api-reference.md +117 -0
- package/documentation/configuration.md +87 -0
- package/documentation/content-safety.md +51 -0
- package/documentation/embeddings-and-rag.md +105 -0
- package/documentation/evals-and-testing.md +56 -0
- package/documentation/getting-started.md +96 -0
- package/documentation/guardrails-events-telemetry.md +72 -0
- package/documentation/jobs-and-realtime.md +69 -0
- package/documentation/memory.md +101 -0
- package/documentation/multimodal.md +49 -0
- package/documentation/orchestration-and-mcp.md +68 -0
- package/documentation/prompts.md +51 -0
- package/documentation/reliability.md +90 -0
- package/documentation/structured-output-and-streaming.md +81 -0
- package/package.json +146 -0
- package/skill/nestjs-ai/SKILL.md +154 -0
package/dist/index.d.cts
ADDED
|
@@ -0,0 +1,1441 @@
|
|
|
1
|
+
import { DynamicModule, OnModuleInit, Type, NestInterceptor, ExecutionContext, CallHandler, OnModuleDestroy } from '@nestjs/common';
|
|
2
|
+
import { A as AiModuleOptions, a as AiModuleAsyncOptions, b as AiFeatureOptions, P as PromptRef, c as PromptDefinition, U as UsageLike } from './ai-module-options.interface-B5X4AFLC.cjs';
|
|
3
|
+
export { C as ConversationStoreProvider, D as DEFAULT_PRICING, M as ModelPricing, d as PricingTable, e as ProviderConfig, f as ProvidersConfig, g as bareModelId, h as costOf, i as interpolate } from './ai-module-options.interface-B5X4AFLC.cjs';
|
|
4
|
+
import * as ai from 'ai';
|
|
5
|
+
import { LanguageModel, EmbeddingModel, ImageModel, RerankingModel, SpeechModel, TranscriptionModel, StepResult, LanguageModelUsage, FinishReason, Tool as Tool$1, ToolSet, generateText, streamText, generateObject, streamObject, LanguageModelMiddleware } from 'ai';
|
|
6
|
+
import { DiscoveryService, MetadataScanner, Reflector } from '@nestjs/core';
|
|
7
|
+
import { ZodType } from 'zod';
|
|
8
|
+
import { A as AiMessage, a as AiInput, C as ConversationStore } from './conversation-store.interface-CtQY-qcc.cjs';
|
|
9
|
+
export { t as toMessages } from './conversation-store.interface-CtQY-qcc.cjs';
|
|
10
|
+
import { A as AgentRegistry } from './stream-to-socket-fJphU0WN.cjs';
|
|
11
|
+
export { a as AgentEntry, S as SocketLike, b as StreamToSocketOptions, T as TextStreamLike, s as streamAgentToSocket } from './stream-to-socket-fJphU0WN.cjs';
|
|
12
|
+
import { LanguageModelV3 } from '@ai-sdk/provider';
|
|
13
|
+
import { ServerResponse } from 'node:http';
|
|
14
|
+
import { Observable } from 'rxjs';
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Root module for `@mgvdev/nestjs-ai`. Registered globally so agents, tools and
|
|
18
|
+
* services are available everywhere once configured.
|
|
19
|
+
*/
|
|
20
|
+
declare class AiModule {
|
|
21
|
+
/** Configure the module with static options. */
|
|
22
|
+
static forRoot(options?: AiModuleOptions): DynamicModule;
|
|
23
|
+
/** Configure the module asynchronously (e.g. from `ConfigService`). */
|
|
24
|
+
static forRootAsync(options: AiModuleAsyncOptions): DynamicModule;
|
|
25
|
+
/**
|
|
26
|
+
* Convenience registration of agents / tools / guardrails so they don't have
|
|
27
|
+
* to be added to a consuming module's own `providers` array, plus feature
|
|
28
|
+
* prompts. Discovery still finds providers globally regardless of where they
|
|
29
|
+
* are registered.
|
|
30
|
+
*/
|
|
31
|
+
static forFeature(feature?: AiFeatureOptions): DynamicModule;
|
|
32
|
+
private static build;
|
|
33
|
+
private static coreProviders;
|
|
34
|
+
/**
|
|
35
|
+
* Registers an optional provider (class / factory / value / useClass shape)
|
|
36
|
+
* under `token`, or nothing when not configured.
|
|
37
|
+
*/
|
|
38
|
+
private static tokenProvider;
|
|
39
|
+
private static exportedTokens;
|
|
40
|
+
private static guardrailClasses;
|
|
41
|
+
/** Seeds prompts (and future startup wiring) once dependencies exist. */
|
|
42
|
+
private static initializerProvider;
|
|
43
|
+
/**
|
|
44
|
+
* Optionally resolves `EventEmitter2` from `@nestjs/event-emitter` if the
|
|
45
|
+
* package is installed and its module is imported; otherwise `undefined`.
|
|
46
|
+
*/
|
|
47
|
+
private static eventEmitterProvider;
|
|
48
|
+
private static storeProvider;
|
|
49
|
+
private static vectorStoreProvider;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
/**
|
|
53
|
+
* Dependency-injection tokens used across the module.
|
|
54
|
+
*/
|
|
55
|
+
declare const AI_MODULE_OPTIONS: unique symbol;
|
|
56
|
+
declare const CONVERSATION_STORE: unique symbol;
|
|
57
|
+
declare const VECTOR_STORE: unique symbol;
|
|
58
|
+
declare const AI_CACHE: unique symbol;
|
|
59
|
+
declare const APPROVAL_GATE: unique symbol;
|
|
60
|
+
declare const AGENT_QUEUE: unique symbol;
|
|
61
|
+
declare const RATE_LIMITER: unique symbol;
|
|
62
|
+
declare const RERANKER: unique symbol;
|
|
63
|
+
/**
|
|
64
|
+
* Default number of tool-calling steps allowed before an agent run stops.
|
|
65
|
+
*/
|
|
66
|
+
declare const DEFAULT_MAX_STEPS = 5;
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Pluggable cache for language-model responses and embeddings. Implement this
|
|
70
|
+
* (e.g. Redis) and register it via `AiModule.forRoot({ cache })`.
|
|
71
|
+
*/
|
|
72
|
+
interface AiCache {
|
|
73
|
+
/** Returns the cached value, or `undefined` on a miss / expiry. */
|
|
74
|
+
get(key: string): Promise<unknown | undefined>;
|
|
75
|
+
/** Stores a value with an optional time-to-live in milliseconds. */
|
|
76
|
+
set(key: string, value: unknown, ttlMs?: number): Promise<void>;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
/**
|
|
80
|
+
* Instantiates and caches the configured `@ai-sdk/*` providers, and resolves
|
|
81
|
+
* `"provider:model"` strings into concrete language / embedding models.
|
|
82
|
+
*
|
|
83
|
+
* Provider packages are imported lazily on module init so only the SDKs a
|
|
84
|
+
* project actually configures need to be installed.
|
|
85
|
+
*/
|
|
86
|
+
declare class ProviderRegistry implements OnModuleInit {
|
|
87
|
+
private readonly options;
|
|
88
|
+
private readonly cache?;
|
|
89
|
+
private readonly providers;
|
|
90
|
+
constructor(options: AiModuleOptions, cache?: AiCache | undefined);
|
|
91
|
+
/** Wraps a model with the cache middleware when a cache is configured. */
|
|
92
|
+
private applyCache;
|
|
93
|
+
onModuleInit(): Promise<void>;
|
|
94
|
+
/**
|
|
95
|
+
* Resolves a language model. Accepts a `LanguageModel` instance (returned
|
|
96
|
+
* as-is), a `"provider:model"` string, a bare `"model"` string (using the
|
|
97
|
+
* default provider), or `undefined` (using `defaultModel`).
|
|
98
|
+
*/
|
|
99
|
+
getLanguageModel(model?: string | LanguageModel | Array<string | LanguageModel>): LanguageModel;
|
|
100
|
+
/** Resolves a single (non-array) model reference without cache wrapping. */
|
|
101
|
+
private resolveSingle;
|
|
102
|
+
/**
|
|
103
|
+
* Resolves an embedding model from a `"provider:model"` string, a bare model
|
|
104
|
+
* string, an `EmbeddingModel` instance, or `undefined` (using
|
|
105
|
+
* `defaultEmbeddingModel`).
|
|
106
|
+
*/
|
|
107
|
+
getEmbeddingModel(model?: string | EmbeddingModel): EmbeddingModel;
|
|
108
|
+
/** Resolves an image-generation model (default `defaultImageModel`). */
|
|
109
|
+
getImageModel(model?: string | ImageModel): ImageModel;
|
|
110
|
+
/** Resolves a reranking model (default `rerankingModel` option). */
|
|
111
|
+
getRerankingModel(model?: string | RerankingModel): RerankingModel;
|
|
112
|
+
/** Resolves a speech (text-to-speech) model (default `defaultSpeechModel`). */
|
|
113
|
+
getSpeechModel(model?: string | SpeechModel): SpeechModel;
|
|
114
|
+
/** Resolves a transcription (speech-to-text) model. */
|
|
115
|
+
getTranscriptionModel(model?: string | TranscriptionModel): TranscriptionModel;
|
|
116
|
+
/**
|
|
117
|
+
* Shared resolution for multimodal models: resolves the provider, then calls
|
|
118
|
+
* the first available factory method (standard name, then shorthand).
|
|
119
|
+
*/
|
|
120
|
+
private resolveMultimodal;
|
|
121
|
+
private resolve;
|
|
122
|
+
private parseProviderName;
|
|
123
|
+
private parseModelId;
|
|
124
|
+
private initProvider;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
/** Minimal shape of `EventEmitter2` from `@nestjs/event-emitter`. */
|
|
128
|
+
interface EventEmitterLike {
|
|
129
|
+
emit(event: string, payload: unknown): boolean;
|
|
130
|
+
}
|
|
131
|
+
/** Injection token for an optional event emitter (EventEmitter2). */
|
|
132
|
+
declare const EVENT_EMITTER: unique symbol;
|
|
133
|
+
/**
|
|
134
|
+
* Emits library events through `@nestjs/event-emitter`'s `EventEmitter2` when
|
|
135
|
+
* it is available, and is a no-op otherwise. This keeps `@nestjs/event-emitter`
|
|
136
|
+
* a truly optional peer dependency.
|
|
137
|
+
*/
|
|
138
|
+
declare class AiEventEmitter {
|
|
139
|
+
private readonly emitter?;
|
|
140
|
+
constructor(emitter?: EventEmitterLike | undefined);
|
|
141
|
+
emit(event: string, payload: unknown): void;
|
|
142
|
+
/** Whether an underlying emitter is wired up. */
|
|
143
|
+
get enabled(): boolean;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
/**
|
|
147
|
+
* Per-call overrides for an agent `.run()` / `.stream()`.
|
|
148
|
+
*/
|
|
149
|
+
interface AgentRunOptions {
|
|
150
|
+
/** Override the agent's model for this call. Array = fallback chain. */
|
|
151
|
+
model?: string | string[];
|
|
152
|
+
/** Retry count forwarded to the underlying generate/stream call. */
|
|
153
|
+
maxRetries?: number;
|
|
154
|
+
/** Override the agent's system prompt for this call. */
|
|
155
|
+
system?: string;
|
|
156
|
+
/** Resolve the system prompt from the PromptRegistry (overrides `system`). */
|
|
157
|
+
systemPrompt?: PromptRef;
|
|
158
|
+
/**
|
|
159
|
+
* Recall relevant snippets from semantic memory and prepend them as context.
|
|
160
|
+
* Requires `conversationId` and a `SemanticMemory` service.
|
|
161
|
+
*/
|
|
162
|
+
recall?: {
|
|
163
|
+
query?: string;
|
|
164
|
+
topK?: number;
|
|
165
|
+
};
|
|
166
|
+
/**
|
|
167
|
+
* Conversation id. When set, prior messages are loaded from the
|
|
168
|
+
* `ConversationStore` before the call and the new exchange is persisted after.
|
|
169
|
+
*/
|
|
170
|
+
conversationId?: string;
|
|
171
|
+
/** Override the maximum tool-calling steps. */
|
|
172
|
+
maxSteps?: number;
|
|
173
|
+
/** Structured-output schema for this call (overrides the agent's `output`). */
|
|
174
|
+
schema?: ZodType<any, any, any>;
|
|
175
|
+
/** Sampling temperature. */
|
|
176
|
+
temperature?: number;
|
|
177
|
+
/** Abort signal to cancel the underlying request. */
|
|
178
|
+
abortSignal?: AbortSignal;
|
|
179
|
+
}
|
|
180
|
+
/**
|
|
181
|
+
* Result of an agent `.run()`.
|
|
182
|
+
*/
|
|
183
|
+
interface AgentResult<T = unknown> {
|
|
184
|
+
/** Generated text (empty string for structured-output runs). */
|
|
185
|
+
text: string;
|
|
186
|
+
/** Parsed structured object, present only for structured-output runs. */
|
|
187
|
+
object?: T;
|
|
188
|
+
/** Per-step details for multi-step tool runs. */
|
|
189
|
+
steps?: StepResult<any>[];
|
|
190
|
+
/** Tool calls made during the run. */
|
|
191
|
+
toolCalls?: unknown[];
|
|
192
|
+
/** Aggregate token usage across all steps. */
|
|
193
|
+
usage?: LanguageModelUsage;
|
|
194
|
+
/** Why generation stopped. */
|
|
195
|
+
finishReason?: FinishReason;
|
|
196
|
+
/** Assistant/tool messages produced by the run. */
|
|
197
|
+
messages: AiMessage[];
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
/** Mutable context passed to guardrails before an agent run. */
|
|
201
|
+
interface GuardrailContext {
|
|
202
|
+
agent: string;
|
|
203
|
+
/** Messages to be sent; a guardrail may mutate this array in place. */
|
|
204
|
+
messages: AiMessage[];
|
|
205
|
+
options: AgentRunOptions;
|
|
206
|
+
}
|
|
207
|
+
/**
|
|
208
|
+
* A guardrail can inspect, mutate, or block agent runs and tool calls. Throw
|
|
209
|
+
* from any hook to abort the run. Register guardrails via
|
|
210
|
+
* `AiModule.forRoot({ guardrails })` or `forFeature({ guardrails })`.
|
|
211
|
+
*/
|
|
212
|
+
interface Guardrail$1 {
|
|
213
|
+
/** Runs before generation. Mutate `ctx.messages` or throw to block. */
|
|
214
|
+
beforeRun?(ctx: GuardrailContext): void | Promise<void>;
|
|
215
|
+
/** Runs after generation with the result. */
|
|
216
|
+
afterRun?(ctx: GuardrailContext, result: AgentResult): void | Promise<void>;
|
|
217
|
+
/** Runs before a tool executes. Throw to block the tool call. */
|
|
218
|
+
onToolCall?(tool: string, args: unknown): void | Promise<void>;
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
/**
|
|
222
|
+
* Collects all `@Guardrail`-decorated providers and runs their hooks in
|
|
223
|
+
* registration order around agent execution.
|
|
224
|
+
*/
|
|
225
|
+
declare class GuardrailRegistry implements OnModuleInit {
|
|
226
|
+
private readonly discovery;
|
|
227
|
+
private readonly guardrails;
|
|
228
|
+
constructor(discovery: DiscoveryService);
|
|
229
|
+
onModuleInit(): void;
|
|
230
|
+
get count(): number;
|
|
231
|
+
runBeforeRun(ctx: GuardrailContext): Promise<void>;
|
|
232
|
+
runAfterRun(ctx: GuardrailContext, result: AgentResult): Promise<void>;
|
|
233
|
+
runOnToolCall(tool: string, args: unknown): Promise<void>;
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
/** Context passed to an approval gate for a tool call awaiting approval. */
|
|
237
|
+
interface ApprovalContext {
|
|
238
|
+
tool: string;
|
|
239
|
+
args: unknown;
|
|
240
|
+
/** Name of the agent making the call, when available. */
|
|
241
|
+
agent?: string;
|
|
242
|
+
}
|
|
243
|
+
/**
|
|
244
|
+
* Decides whether a tool flagged `requiresApproval` may execute. Implement this
|
|
245
|
+
* to plug in human-in-the-loop approval (e.g. block on a queue, check a policy)
|
|
246
|
+
* and register it via `AiModule.forRoot({ approvalGate })`.
|
|
247
|
+
*/
|
|
248
|
+
interface ApprovalGate {
|
|
249
|
+
/** Resolve `true` to allow the tool call, `false` to block it. */
|
|
250
|
+
requestApproval(context: ApprovalContext): Promise<boolean>;
|
|
251
|
+
}
|
|
252
|
+
/** Thrown when an approval gate denies a tool call. */
|
|
253
|
+
declare class ToolApprovalDeniedError extends Error {
|
|
254
|
+
readonly tool: string;
|
|
255
|
+
constructor(tool: string);
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
/** A discovered tool together with the class that declared it. */
|
|
259
|
+
interface ToolEntry {
|
|
260
|
+
name: string;
|
|
261
|
+
tool: Tool$1<any, any>;
|
|
262
|
+
target: Type<any>;
|
|
263
|
+
}
|
|
264
|
+
/** A tool reference accepted by `buildToolSet`: a provider class or a name. */
|
|
265
|
+
type ToolRef = Type<any> | string;
|
|
266
|
+
/**
|
|
267
|
+
* Discovers every `@Tool`-decorated method across the application's providers
|
|
268
|
+
* and wraps each into a Vercel AI SDK `tool()` whose `execute` calls the method
|
|
269
|
+
* on its DI-managed instance (preserving `this` and injected dependencies).
|
|
270
|
+
*/
|
|
271
|
+
declare class ToolRegistry implements OnModuleInit {
|
|
272
|
+
private readonly discovery;
|
|
273
|
+
private readonly scanner;
|
|
274
|
+
private readonly reflector;
|
|
275
|
+
private readonly events?;
|
|
276
|
+
private readonly guardrails?;
|
|
277
|
+
private readonly approvalGate?;
|
|
278
|
+
private readonly agentRegistry?;
|
|
279
|
+
private readonly tools;
|
|
280
|
+
constructor(discovery: DiscoveryService, scanner: MetadataScanner, reflector: Reflector, events?: AiEventEmitter | undefined, guardrails?: GuardrailRegistry | undefined, approvalGate?: ApprovalGate | undefined, agentRegistry?: AgentRegistry | undefined);
|
|
281
|
+
onModuleInit(): void;
|
|
282
|
+
private register;
|
|
283
|
+
/** Returns the tool registered under `name`, if any. */
|
|
284
|
+
getByName(name: string): ToolEntry | undefined;
|
|
285
|
+
/** Returns every tool declared by the given provider class. */
|
|
286
|
+
getForClass(target: Type<any>): ToolEntry[];
|
|
287
|
+
/** Returns all discovered tools. */
|
|
288
|
+
getAll(): ToolEntry[];
|
|
289
|
+
/**
|
|
290
|
+
* Builds the `ToolSet` passed to `generateText`/`streamText` from a list of
|
|
291
|
+
* tool references (provider classes and/or tool names). Passing no refs
|
|
292
|
+
* returns every discovered tool.
|
|
293
|
+
*/
|
|
294
|
+
buildToolSet(refs?: ToolRef[]): ToolSet;
|
|
295
|
+
private resolveRef;
|
|
296
|
+
private resolveAgentRef;
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
/** Replaces `model` (a resolvable id) and `tools` (tool refs) on SDK params. */
|
|
300
|
+
type NestAiParams<Fn extends (arg: any) => any> = Omit<Parameters<Fn>[0], 'model' | 'tools'> & {
|
|
301
|
+
/** Model id string (e.g. `"openai:gpt-4o"`); defaults to the module model. */
|
|
302
|
+
model?: string;
|
|
303
|
+
/** Tool references (provider classes and/or names) to expose to the model. */
|
|
304
|
+
tools?: ToolRef[];
|
|
305
|
+
};
|
|
306
|
+
/**
|
|
307
|
+
* Thin, DI-friendly facade over the Vercel AI SDK generation functions for
|
|
308
|
+
* callers that don't want to declare an `@Agent` class. Resolves `model`
|
|
309
|
+
* strings and `tools` references, then forwards everything else unchanged.
|
|
310
|
+
*/
|
|
311
|
+
declare class AiService {
|
|
312
|
+
private readonly providers;
|
|
313
|
+
private readonly toolRegistry;
|
|
314
|
+
constructor(providers: ProviderRegistry, toolRegistry: ToolRegistry);
|
|
315
|
+
generateText(params: NestAiParams<typeof generateText>): ReturnType<typeof generateText>;
|
|
316
|
+
streamText(params: NestAiParams<typeof streamText>): ReturnType<typeof streamText>;
|
|
317
|
+
generateObject(params: NestAiParams<typeof generateObject>): ReturnType<typeof generateObject>;
|
|
318
|
+
streamObject(params: NestAiParams<typeof streamObject>): ReturnType<typeof streamObject>;
|
|
319
|
+
private resolve;
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
/**
|
|
323
|
+
* Options accepted by the `@Tool` decorator.
|
|
324
|
+
*/
|
|
325
|
+
interface ToolOptions {
|
|
326
|
+
/** Tool name exposed to the model. Defaults to the method name. */
|
|
327
|
+
name?: string;
|
|
328
|
+
/** Human-readable description the model uses to decide when to call it. */
|
|
329
|
+
description: string;
|
|
330
|
+
/** Zod schema describing the tool's input arguments. */
|
|
331
|
+
schema: ZodType<any, any, any>;
|
|
332
|
+
/** Require approval from the configured `ApprovalGate` before executing. */
|
|
333
|
+
requiresApproval?: boolean;
|
|
334
|
+
}
|
|
335
|
+
/**
|
|
336
|
+
* Metadata stored on a `@Tool`-decorated method.
|
|
337
|
+
*/
|
|
338
|
+
interface ToolMetadata extends ToolOptions {
|
|
339
|
+
methodName: string;
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
/**
|
|
343
|
+
* Marks a method of an injectable provider as an AI tool (a.k.a. function
|
|
344
|
+
* call). The method receives the validated arguments (typed by the Zod
|
|
345
|
+
* `schema`) and its return value is fed back to the model.
|
|
346
|
+
*
|
|
347
|
+
* Because the owning class is a normal NestJS provider, the method keeps full
|
|
348
|
+
* access to injected dependencies.
|
|
349
|
+
*
|
|
350
|
+
* @example
|
|
351
|
+
* ```ts
|
|
352
|
+
* @Injectable()
|
|
353
|
+
* class WeatherTools {
|
|
354
|
+
* constructor(private readonly api: WeatherApi) {}
|
|
355
|
+
*
|
|
356
|
+
* @Tool({ description: 'Get the weather for a city', schema: z.object({ city: z.string() }) })
|
|
357
|
+
* getWeather({ city }: { city: string }) {
|
|
358
|
+
* return this.api.lookup(city);
|
|
359
|
+
* }
|
|
360
|
+
* }
|
|
361
|
+
* ```
|
|
362
|
+
*/
|
|
363
|
+
declare function Tool(options: ToolOptions): MethodDecorator;
|
|
364
|
+
|
|
365
|
+
/**
|
|
366
|
+
* Configuration provided to the `@Agent` class decorator.
|
|
367
|
+
*/
|
|
368
|
+
interface AgentOptions {
|
|
369
|
+
/** Model id, e.g. `"openai:gpt-4o"`. Array = fallback chain. */
|
|
370
|
+
model?: string | string[];
|
|
371
|
+
/** System prompt establishing the agent's role and behavior. */
|
|
372
|
+
system?: string;
|
|
373
|
+
/** Tools the agent may call: provider classes and/or tool names. */
|
|
374
|
+
tools?: ToolRef[];
|
|
375
|
+
/** Maximum tool-calling steps before the run stops. */
|
|
376
|
+
maxSteps?: number;
|
|
377
|
+
/** Default Zod schema for structured output. Enables object generation. */
|
|
378
|
+
output?: ZodType<any, any, any>;
|
|
379
|
+
}
|
|
380
|
+
|
|
381
|
+
/**
|
|
382
|
+
* Declares a class as an AI agent. The class should extend {@link AiAgent} to
|
|
383
|
+
* gain `.run()` / `.stream()`. `@Agent` also marks the class `@Injectable`, so
|
|
384
|
+
* it participates in DI and can inject its own dependencies.
|
|
385
|
+
*
|
|
386
|
+
* @example
|
|
387
|
+
* ```ts
|
|
388
|
+
* @Agent({
|
|
389
|
+
* model: 'openai:gpt-4o',
|
|
390
|
+
* system: 'You are a helpful support assistant.',
|
|
391
|
+
* tools: [WeatherTools],
|
|
392
|
+
* })
|
|
393
|
+
* export class SupportAgent extends AiAgent {}
|
|
394
|
+
* ```
|
|
395
|
+
*/
|
|
396
|
+
declare function Agent(options?: AgentOptions): ClassDecorator;
|
|
397
|
+
|
|
398
|
+
/**
|
|
399
|
+
* In-memory registry of named, versioned prompt templates. Register prompts via
|
|
400
|
+
* `AiModule.forRoot({ prompts })`, `AiModule.forFeature({ prompts })`, or
|
|
401
|
+
* imperatively, then `render(name, vars)` to produce a final string.
|
|
402
|
+
*/
|
|
403
|
+
declare class PromptRegistry {
|
|
404
|
+
/** name -> (version -> definition) */
|
|
405
|
+
private readonly prompts;
|
|
406
|
+
/** name -> most recently registered version key */
|
|
407
|
+
private readonly latest;
|
|
408
|
+
/** Registers a prompt. Throws on a duplicate (name, version). */
|
|
409
|
+
register(definition: PromptDefinition): void;
|
|
410
|
+
/** Registers many prompts. */
|
|
411
|
+
registerAll(definitions: PromptDefinition[]): void;
|
|
412
|
+
/** Returns a prompt definition (latest version when `version` omitted). */
|
|
413
|
+
get(name: string, version?: string): PromptDefinition;
|
|
414
|
+
/** Renders a prompt to a string, interpolating `{{var}}` placeholders. */
|
|
415
|
+
render(name: string, vars?: Record<string, unknown>, options?: {
|
|
416
|
+
version?: string;
|
|
417
|
+
}): string;
|
|
418
|
+
/** Whether a prompt (any version) is registered. */
|
|
419
|
+
has(name: string): boolean;
|
|
420
|
+
}
|
|
421
|
+
|
|
422
|
+
/** Accumulated usage totals for a scope (conversation or global). */
|
|
423
|
+
interface UsageTotals {
|
|
424
|
+
inputTokens: number;
|
|
425
|
+
outputTokens: number;
|
|
426
|
+
cost: number;
|
|
427
|
+
runs: number;
|
|
428
|
+
}
|
|
429
|
+
/** A single recorded run's usage. */
|
|
430
|
+
interface UsageRecord extends UsageTotals {
|
|
431
|
+
conversationId?: string;
|
|
432
|
+
agent?: string;
|
|
433
|
+
model: string;
|
|
434
|
+
}
|
|
435
|
+
/**
|
|
436
|
+
* Tracks token usage and USD cost per conversation (and globally), and emits an
|
|
437
|
+
* `ai.usage` event per recorded run.
|
|
438
|
+
*/
|
|
439
|
+
declare class UsageTracker {
|
|
440
|
+
private readonly options;
|
|
441
|
+
private readonly events?;
|
|
442
|
+
private readonly totalsByScope;
|
|
443
|
+
constructor(options: AiModuleOptions, events?: AiEventEmitter | undefined);
|
|
444
|
+
/** Records a run's usage, returns the single-run record, emits `ai.usage`. */
|
|
445
|
+
record(entry: {
|
|
446
|
+
model: string;
|
|
447
|
+
usage: UsageLike | undefined;
|
|
448
|
+
conversationId?: string;
|
|
449
|
+
agent?: string;
|
|
450
|
+
}): UsageRecord;
|
|
451
|
+
/** Totals for a conversation, or global totals when no id is given. */
|
|
452
|
+
totals(conversationId?: string): UsageTotals;
|
|
453
|
+
/** Clears totals for a conversation (or all when no id). */
|
|
454
|
+
reset(conversationId?: string): void;
|
|
455
|
+
}
|
|
456
|
+
|
|
457
|
+
interface EmbedOptions {
|
|
458
|
+
/** Embedding model id, e.g. `"openai:text-embedding-3-small"`. */
|
|
459
|
+
model?: string;
|
|
460
|
+
abortSignal?: AbortSignal;
|
|
461
|
+
maxRetries?: number;
|
|
462
|
+
}
|
|
463
|
+
/**
|
|
464
|
+
* Generates vector embeddings for semantic search, clustering, and similarity.
|
|
465
|
+
* Wraps the Vercel AI SDK's `embed` / `embedMany`.
|
|
466
|
+
*/
|
|
467
|
+
declare class EmbeddingsService {
|
|
468
|
+
private readonly providers;
|
|
469
|
+
private readonly cache?;
|
|
470
|
+
constructor(providers: ProviderRegistry, cache?: AiCache | undefined);
|
|
471
|
+
/** Embeds a single value (cached when a cache is configured). */
|
|
472
|
+
embed(value: string, options?: EmbedOptions): Promise<ai.EmbedResult>;
|
|
473
|
+
/** Embeds many values (the SDK batches automatically). */
|
|
474
|
+
embedMany(values: string[], options?: EmbedOptions): Promise<ai.EmbedManyResult>;
|
|
475
|
+
}
|
|
476
|
+
|
|
477
|
+
/** A document stored in a vector store. */
|
|
478
|
+
interface VectorDocument {
|
|
479
|
+
id: string;
|
|
480
|
+
content: string;
|
|
481
|
+
/** Precomputed embedding. Required by stores that don't embed themselves. */
|
|
482
|
+
embedding?: number[];
|
|
483
|
+
metadata?: Record<string, unknown>;
|
|
484
|
+
}
|
|
485
|
+
/** A single similarity-search hit. */
|
|
486
|
+
interface VectorQueryResult {
|
|
487
|
+
id: string;
|
|
488
|
+
content: string;
|
|
489
|
+
/** Similarity score (higher is closer). */
|
|
490
|
+
score: number;
|
|
491
|
+
metadata?: Record<string, unknown>;
|
|
492
|
+
}
|
|
493
|
+
/** Options for a vector similarity query. */
|
|
494
|
+
interface VectorQueryOptions {
|
|
495
|
+
/** Maximum number of results to return (default 4). */
|
|
496
|
+
topK?: number;
|
|
497
|
+
/** Optional metadata equality filter. */
|
|
498
|
+
filter?: Record<string, unknown>;
|
|
499
|
+
}
|
|
500
|
+
/**
|
|
501
|
+
* Persistence + similarity-search contract for RAG. Implement this to back
|
|
502
|
+
* retrieval with pgvector, a managed vector DB, etc., then register it via
|
|
503
|
+
* `AiModule.forRoot({ vectorStore })`.
|
|
504
|
+
*/
|
|
505
|
+
interface VectorStore {
|
|
506
|
+
/** Inserts or replaces documents by id. */
|
|
507
|
+
upsert(documents: VectorDocument[]): Promise<void>;
|
|
508
|
+
/** Returns the closest documents to `embedding`, ranked by similarity. */
|
|
509
|
+
query(embedding: number[], options?: VectorQueryOptions): Promise<VectorQueryResult[]>;
|
|
510
|
+
/** Removes documents by id. */
|
|
511
|
+
delete(ids: string[]): Promise<void>;
|
|
512
|
+
/** Removes all documents. */
|
|
513
|
+
clear(): Promise<void>;
|
|
514
|
+
}
|
|
515
|
+
|
|
516
|
+
interface RecallOptions {
|
|
517
|
+
topK?: number;
|
|
518
|
+
model?: string;
|
|
519
|
+
}
|
|
520
|
+
/**
|
|
521
|
+
* Long-term semantic memory: stores snippets per conversation as embeddings and
|
|
522
|
+
* recalls the most relevant ones for a query. Backed by the configured
|
|
523
|
+
* `VectorStore` (isolated per conversation via metadata).
|
|
524
|
+
*/
|
|
525
|
+
declare class SemanticMemory {
|
|
526
|
+
private readonly embeddings;
|
|
527
|
+
private readonly store;
|
|
528
|
+
private readonly ai?;
|
|
529
|
+
constructor(embeddings: EmbeddingsService, store: VectorStore, ai?: AiService | undefined);
|
|
530
|
+
/** Embeds and stores a snippet under a conversation. */
|
|
531
|
+
remember(conversationId: string, text: string, options?: {
|
|
532
|
+
model?: string;
|
|
533
|
+
metadata?: Record<string, unknown>;
|
|
534
|
+
}): Promise<void>;
|
|
535
|
+
/** Returns the most relevant stored snippets for a query. */
|
|
536
|
+
recall(conversationId: string, query: string, options?: RecallOptions): Promise<VectorQueryResult[]>;
|
|
537
|
+
/**
|
|
538
|
+
* Summarizes messages with the LLM (requires `AiService`), then stores the
|
|
539
|
+
* summary as a memory snippet. Returns the stored text.
|
|
540
|
+
*/
|
|
541
|
+
rememberConversation(conversationId: string, input: AiInput, options?: {
|
|
542
|
+
summarize?: boolean;
|
|
543
|
+
model?: string;
|
|
544
|
+
}): Promise<string>;
|
|
545
|
+
/** Summarizes messages into a compact string via the LLM. */
|
|
546
|
+
summarize(input: AiInput, model?: string): Promise<string>;
|
|
547
|
+
}
|
|
548
|
+
|
|
549
|
+
/**
|
|
550
|
+
* Runtime that executes `@Agent` classes: resolves their model, tools and
|
|
551
|
+
* memory, then drives the Vercel AI SDK (`generateText` / `streamText`, or the
|
|
552
|
+
* object variants when a structured-output schema is present).
|
|
553
|
+
*/
|
|
554
|
+
declare class AgentExecutorService {
|
|
555
|
+
private readonly providers;
|
|
556
|
+
private readonly toolRegistry;
|
|
557
|
+
private readonly store;
|
|
558
|
+
private readonly options;
|
|
559
|
+
private readonly events?;
|
|
560
|
+
private readonly guardrails?;
|
|
561
|
+
private readonly prompts?;
|
|
562
|
+
private readonly usageTracker?;
|
|
563
|
+
private readonly semanticMemory?;
|
|
564
|
+
constructor(providers: ProviderRegistry, toolRegistry: ToolRegistry, store: ConversationStore, options: AiModuleOptions, events?: AiEventEmitter | undefined, guardrails?: GuardrailRegistry | undefined, prompts?: PromptRegistry | undefined, usageTracker?: UsageTracker | undefined, semanticMemory?: SemanticMemory | undefined);
|
|
565
|
+
/** Runs an agent to completion and returns its result. */
|
|
566
|
+
run<T = unknown>(agent: object, input: AiInput, opts?: AgentRunOptions): Promise<AgentResult<T>>;
|
|
567
|
+
private runObject;
|
|
568
|
+
private runText;
|
|
569
|
+
/**
|
|
570
|
+
* Streams an agent's response. Returns the raw Vercel stream result so
|
|
571
|
+
* controllers can pipe it to an HTTP response or iterate `textStream`.
|
|
572
|
+
* Conversation persistence happens on stream finish.
|
|
573
|
+
*/
|
|
574
|
+
stream(agent: object, input: AiInput, opts?: AgentRunOptions): ReturnType<typeof streamText> | ReturnType<typeof streamObject>;
|
|
575
|
+
/** Resolves the system prompt and prepends recalled memory when requested. */
|
|
576
|
+
private resolveSystemWithRecall;
|
|
577
|
+
private resolveSystem;
|
|
578
|
+
private telemetry;
|
|
579
|
+
private readMetadata;
|
|
580
|
+
private resolveMaxSteps;
|
|
581
|
+
private loadHistory;
|
|
582
|
+
private persist;
|
|
583
|
+
}
|
|
584
|
+
|
|
585
|
+
/**
|
|
586
|
+
* Base class for `@Agent`-decorated agents. Provides `.run()` and `.stream()`
|
|
587
|
+
* by delegating to the {@link AgentExecutorService}, which is property-injected
|
|
588
|
+
* so subclasses need no constructor boilerplate.
|
|
589
|
+
*
|
|
590
|
+
* @example
|
|
591
|
+
* ```ts
|
|
592
|
+
* @Agent({ model: 'openai:gpt-4o', system: 'You are helpful.' })
|
|
593
|
+
* class ChatAgent extends AiAgent {}
|
|
594
|
+
*
|
|
595
|
+
* // elsewhere
|
|
596
|
+
* const { text } = await chatAgent.run('Hello!');
|
|
597
|
+
* ```
|
|
598
|
+
*/
|
|
599
|
+
declare abstract class AiAgent {
|
|
600
|
+
protected readonly executor: AgentExecutorService;
|
|
601
|
+
/** Runs the agent to completion. */
|
|
602
|
+
run<T = unknown>(input: AiInput, opts?: AgentRunOptions): Promise<AgentResult<T>>;
|
|
603
|
+
/** Streams the agent's response (returns the raw Vercel stream result). */
|
|
604
|
+
stream(input: AiInput, opts?: AgentRunOptions): ReturnType<AgentExecutorService['stream']>;
|
|
605
|
+
}
|
|
606
|
+
|
|
607
|
+
/**
|
|
608
|
+
* Default in-process conversation store. Suitable for development, tests, and
|
|
609
|
+
* single-instance deployments. History is lost on restart and not shared
|
|
610
|
+
* across processes — provide a persistent implementation for production.
|
|
611
|
+
*/
|
|
612
|
+
declare class InMemoryConversationStore implements ConversationStore {
|
|
613
|
+
private readonly conversations;
|
|
614
|
+
load(conversationId: string): Promise<AiMessage[]>;
|
|
615
|
+
append(conversationId: string, messages: AiMessage[]): Promise<void>;
|
|
616
|
+
clear(conversationId: string): Promise<void>;
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
interface GenerateImageOptions {
|
|
620
|
+
/** Image model id, e.g. `"openai:dall-e-3"`. Defaults to `defaultImageModel`. */
|
|
621
|
+
model?: string;
|
|
622
|
+
/** Number of images to generate. */
|
|
623
|
+
n?: number;
|
|
624
|
+
/** Size string, e.g. `"1024x1024"`. */
|
|
625
|
+
size?: `${number}x${number}`;
|
|
626
|
+
/** Aspect ratio, e.g. `"16:9"`. */
|
|
627
|
+
aspectRatio?: `${number}:${number}`;
|
|
628
|
+
seed?: number;
|
|
629
|
+
providerOptions?: Record<string, Record<string, any>>;
|
|
630
|
+
abortSignal?: AbortSignal;
|
|
631
|
+
maxRetries?: number;
|
|
632
|
+
}
|
|
633
|
+
/**
|
|
634
|
+
* Generates images from a text prompt. Wraps the Vercel AI SDK's
|
|
635
|
+
* `experimental_generateImage`. Result exposes `.image` and `.images`.
|
|
636
|
+
*/
|
|
637
|
+
declare class ImageService {
|
|
638
|
+
private readonly providers;
|
|
639
|
+
constructor(providers: ProviderRegistry);
|
|
640
|
+
generate(prompt: string, options?: GenerateImageOptions): Promise<ai.GenerateImageResult>;
|
|
641
|
+
}
|
|
642
|
+
|
|
643
|
+
interface GenerateSpeechOptions {
|
|
644
|
+
/** Speech model id, e.g. `"openai:tts-1"`. Defaults to `defaultSpeechModel`. */
|
|
645
|
+
model?: string;
|
|
646
|
+
/** Voice identifier (provider-specific). */
|
|
647
|
+
voice?: string;
|
|
648
|
+
/** Output audio format, e.g. `"mp3"`. */
|
|
649
|
+
outputFormat?: string;
|
|
650
|
+
/** Extra guidance for the synthesis. */
|
|
651
|
+
instructions?: string;
|
|
652
|
+
speed?: number;
|
|
653
|
+
language?: string;
|
|
654
|
+
providerOptions?: Record<string, Record<string, any>>;
|
|
655
|
+
abortSignal?: AbortSignal;
|
|
656
|
+
maxRetries?: number;
|
|
657
|
+
}
|
|
658
|
+
/**
|
|
659
|
+
* Synthesizes speech from text. Wraps the Vercel AI SDK's
|
|
660
|
+
* `experimental_generateSpeech`. Result exposes `.audio`.
|
|
661
|
+
*/
|
|
662
|
+
declare class SpeechService {
|
|
663
|
+
private readonly providers;
|
|
664
|
+
constructor(providers: ProviderRegistry);
|
|
665
|
+
generate(text: string, options?: GenerateSpeechOptions): Promise<ai.SpeechResult>;
|
|
666
|
+
}
|
|
667
|
+
|
|
668
|
+
/** Audio input accepted by the transcription service. */
|
|
669
|
+
type AudioInput = Uint8Array | ArrayBuffer | Buffer | string | URL;
|
|
670
|
+
interface TranscribeOptions {
|
|
671
|
+
/** Transcription model id, e.g. `"openai:whisper-1"`. */
|
|
672
|
+
model?: string;
|
|
673
|
+
providerOptions?: Record<string, Record<string, any>>;
|
|
674
|
+
abortSignal?: AbortSignal;
|
|
675
|
+
maxRetries?: number;
|
|
676
|
+
}
|
|
677
|
+
/**
|
|
678
|
+
* Transcribes audio to text. Wraps the Vercel AI SDK's
|
|
679
|
+
* `experimental_transcribe`. Result exposes `.text` and `.segments`.
|
|
680
|
+
*/
|
|
681
|
+
declare class TranscriptionService {
|
|
682
|
+
private readonly providers;
|
|
683
|
+
constructor(providers: ProviderRegistry);
|
|
684
|
+
transcribe(audio: AudioInput, options?: TranscribeOptions): Promise<ai.TranscriptionResult>;
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
/**
|
|
688
|
+
* In-process vector store ranking by cosine similarity. Suitable for
|
|
689
|
+
* development, tests, and small datasets. Not persistent or shared across
|
|
690
|
+
* processes — provide a durable `VectorStore` for production.
|
|
691
|
+
*/
|
|
692
|
+
declare class InMemoryVectorStore implements VectorStore {
|
|
693
|
+
private readonly documents;
|
|
694
|
+
upsert(documents: VectorDocument[]): Promise<void>;
|
|
695
|
+
query(embedding: number[], options?: VectorQueryOptions): Promise<VectorQueryResult[]>;
|
|
696
|
+
delete(ids: string[]): Promise<void>;
|
|
697
|
+
clear(): Promise<void>;
|
|
698
|
+
private matchesFilter;
|
|
699
|
+
}
|
|
700
|
+
|
|
701
|
+
/**
|
|
702
|
+
* Re-orders retrieval results by relevance to the query, returning the top `topN`.
|
|
703
|
+
*/
|
|
704
|
+
interface Reranker {
|
|
705
|
+
rerank(query: string, results: VectorQueryResult[], topN: number): Promise<VectorQueryResult[]>;
|
|
706
|
+
}
|
|
707
|
+
|
|
708
|
+
/** An item to ingest into the vector store. */
|
|
709
|
+
interface IngestItem {
|
|
710
|
+
/** Base id; chunks are suffixed `#0`, `#1`, … Defaults to a positional id. */
|
|
711
|
+
id?: string;
|
|
712
|
+
content: string;
|
|
713
|
+
metadata?: Record<string, unknown>;
|
|
714
|
+
}
|
|
715
|
+
interface IngestOptions {
|
|
716
|
+
/** Max characters per chunk (default 1000; 0 disables chunking). */
|
|
717
|
+
chunkSize?: number;
|
|
718
|
+
/** Character overlap between consecutive chunks (default 100). */
|
|
719
|
+
chunkOverlap?: number;
|
|
720
|
+
/** Embedding model id. */
|
|
721
|
+
model?: string;
|
|
722
|
+
}
|
|
723
|
+
interface RetrieveOptions {
|
|
724
|
+
topK?: number;
|
|
725
|
+
model?: string;
|
|
726
|
+
filter?: Record<string, unknown>;
|
|
727
|
+
/**
|
|
728
|
+
* Rerank the results before truncating to `topK`. `true` uses the configured
|
|
729
|
+
* default reranker; pass a `Reranker` to override. When reranking, more
|
|
730
|
+
* candidates (`fetchK`) are fetched first.
|
|
731
|
+
*/
|
|
732
|
+
rerank?: boolean | Reranker;
|
|
733
|
+
/** Candidates to fetch before reranking (default `topK * 4`). */
|
|
734
|
+
fetchK?: number;
|
|
735
|
+
}
|
|
736
|
+
/**
|
|
737
|
+
* Retrieval-augmented generation helper: chunk + embed + store documents, and
|
|
738
|
+
* embed queries to fetch the most relevant chunks.
|
|
739
|
+
*/
|
|
740
|
+
declare class RagService {
|
|
741
|
+
private readonly embeddings;
|
|
742
|
+
private readonly store;
|
|
743
|
+
private readonly defaultReranker?;
|
|
744
|
+
constructor(embeddings: EmbeddingsService, store: VectorStore, defaultReranker?: Reranker | undefined);
|
|
745
|
+
/** Chunks, embeds, and upserts items into the vector store. */
|
|
746
|
+
ingest(items: IngestItem[], options?: IngestOptions): Promise<void>;
|
|
747
|
+
/** Embeds `query` and returns the most similar stored chunks. */
|
|
748
|
+
retrieve(query: string, options?: RetrieveOptions): Promise<VectorQueryResult[]>;
|
|
749
|
+
}
|
|
750
|
+
/** Splits text into overlapping fixed-size character chunks. */
|
|
751
|
+
declare function splitText(text: string, chunkSize: number, overlap: number): string[];
|
|
752
|
+
|
|
753
|
+
interface RetrievalToolOptions {
|
|
754
|
+
/** Tool name exposed to the model (default `"searchKnowledgeBase"`). */
|
|
755
|
+
name?: string;
|
|
756
|
+
/** Tool description guiding when the model should search. */
|
|
757
|
+
description?: string;
|
|
758
|
+
/** Number of chunks to return (default 4). */
|
|
759
|
+
topK?: number;
|
|
760
|
+
/** Embedding model id for the query. */
|
|
761
|
+
model?: string;
|
|
762
|
+
/** Optional metadata filter applied to every retrieval. */
|
|
763
|
+
filter?: Record<string, unknown>;
|
|
764
|
+
}
|
|
765
|
+
/**
|
|
766
|
+
* Builds a Vercel AI SDK `tool()` that retrieves relevant chunks from a
|
|
767
|
+
* `RagService`, so an agent can ground its answers. Register it by exposing it
|
|
768
|
+
* from a `@Tool`-style provider, or pass its tool set directly to `AiService`.
|
|
769
|
+
*
|
|
770
|
+
* @example
|
|
771
|
+
* ```ts
|
|
772
|
+
* const tool = createRetrievalTool(rag, { topK: 5 });
|
|
773
|
+
* await ai.generateText({ model: 'openai:gpt-4o', tools: { search: tool }, prompt });
|
|
774
|
+
* ```
|
|
775
|
+
*/
|
|
776
|
+
declare function createRetrievalTool(rag: RagService, options?: RetrievalToolOptions): Tool$1<{
|
|
777
|
+
query: string;
|
|
778
|
+
}, string>;
|
|
779
|
+
|
|
780
|
+
/** Event names emitted by the library (namespaced for `@OnEvent`). */
|
|
781
|
+
declare const AI_EVENTS: {
|
|
782
|
+
readonly agentRunStart: "ai.agent.run.start";
|
|
783
|
+
readonly agentRunFinish: "ai.agent.run.finish";
|
|
784
|
+
readonly agentRunError: "ai.agent.run.error";
|
|
785
|
+
readonly toolCall: "ai.tool.call";
|
|
786
|
+
readonly toolResult: "ai.tool.result";
|
|
787
|
+
readonly streamFinish: "ai.stream.finish";
|
|
788
|
+
readonly usage: "ai.usage";
|
|
789
|
+
};
|
|
790
|
+
interface AgentRunStartPayload {
|
|
791
|
+
agent: string;
|
|
792
|
+
input: unknown;
|
|
793
|
+
options: AgentRunOptions;
|
|
794
|
+
}
|
|
795
|
+
interface AgentRunFinishPayload {
|
|
796
|
+
agent: string;
|
|
797
|
+
result: AgentResult;
|
|
798
|
+
}
|
|
799
|
+
interface AgentRunErrorPayload {
|
|
800
|
+
agent: string;
|
|
801
|
+
error: unknown;
|
|
802
|
+
}
|
|
803
|
+
interface ToolCallPayload {
|
|
804
|
+
tool: string;
|
|
805
|
+
args: unknown;
|
|
806
|
+
}
|
|
807
|
+
interface ToolResultPayload {
|
|
808
|
+
tool: string;
|
|
809
|
+
args: unknown;
|
|
810
|
+
result: unknown;
|
|
811
|
+
}
|
|
812
|
+
|
|
813
|
+
/**
|
|
814
|
+
* Marks an injectable provider as a {@link Guardrail}. Discovered guardrails run
|
|
815
|
+
* on every agent execution. The class may inject its own dependencies.
|
|
816
|
+
*
|
|
817
|
+
* @example
|
|
818
|
+
* ```ts
|
|
819
|
+
* @Guardrail()
|
|
820
|
+
* export class BlockProfanity implements Guardrail {
|
|
821
|
+
* beforeRun(ctx: GuardrailContext) {
|
|
822
|
+
* if (containsProfanity(ctx.messages)) throw new Error('Blocked');
|
|
823
|
+
* }
|
|
824
|
+
* }
|
|
825
|
+
* ```
|
|
826
|
+
*/
|
|
827
|
+
declare function Guardrail(): ClassDecorator;
|
|
828
|
+
|
|
829
|
+
/**
|
|
830
|
+
* Minimal shape of a Prisma model delegate this store needs. Pass your
|
|
831
|
+
* generated delegate (e.g. `prisma.aiMessage`) — no dependency on
|
|
832
|
+
* `@prisma/client` is required by this library.
|
|
833
|
+
*
|
|
834
|
+
* Expected Prisma model:
|
|
835
|
+
* ```prisma
|
|
836
|
+
* model AiMessage {
|
|
837
|
+
* id String @id @default(cuid())
|
|
838
|
+
* conversationId String
|
|
839
|
+
* role String
|
|
840
|
+
* content Json
|
|
841
|
+
* position Int
|
|
842
|
+
* createdAt DateTime @default(now())
|
|
843
|
+
* @@index([conversationId])
|
|
844
|
+
* }
|
|
845
|
+
* ```
|
|
846
|
+
*/
|
|
847
|
+
interface PrismaConversationDelegate {
|
|
848
|
+
findMany(args: {
|
|
849
|
+
where: {
|
|
850
|
+
conversationId: string;
|
|
851
|
+
};
|
|
852
|
+
orderBy: {
|
|
853
|
+
position: 'asc' | 'desc';
|
|
854
|
+
};
|
|
855
|
+
}): Promise<Array<{
|
|
856
|
+
role: string;
|
|
857
|
+
content: unknown;
|
|
858
|
+
}>>;
|
|
859
|
+
create(args: {
|
|
860
|
+
data: {
|
|
861
|
+
conversationId: string;
|
|
862
|
+
role: string;
|
|
863
|
+
content: unknown;
|
|
864
|
+
position: number;
|
|
865
|
+
};
|
|
866
|
+
}): Promise<unknown>;
|
|
867
|
+
count(args: {
|
|
868
|
+
where: {
|
|
869
|
+
conversationId: string;
|
|
870
|
+
};
|
|
871
|
+
}): Promise<number>;
|
|
872
|
+
deleteMany(args: {
|
|
873
|
+
where: {
|
|
874
|
+
conversationId: string;
|
|
875
|
+
};
|
|
876
|
+
}): Promise<unknown>;
|
|
877
|
+
}
|
|
878
|
+
/**
|
|
879
|
+
* Prisma-backed conversation store built on a delegate interface, so it works
|
|
880
|
+
* with any generated Prisma client without a compile-time dependency on it.
|
|
881
|
+
*/
|
|
882
|
+
declare class PrismaConversationStore implements ConversationStore {
|
|
883
|
+
private readonly delegate;
|
|
884
|
+
constructor(delegate: PrismaConversationDelegate);
|
|
885
|
+
load(conversationId: string): Promise<AiMessage[]>;
|
|
886
|
+
append(conversationId: string, messages: AiMessage[]): Promise<void>;
|
|
887
|
+
clear(conversationId: string): Promise<void>;
|
|
888
|
+
}
|
|
889
|
+
|
|
890
|
+
interface FallbackOptions {
|
|
891
|
+
/**
|
|
892
|
+
* Decide whether an error from a model should trigger a fallback to the next
|
|
893
|
+
* one. Defaults to always retrying on the next model.
|
|
894
|
+
*/
|
|
895
|
+
shouldRetry?: (error: unknown) => boolean;
|
|
896
|
+
/** Provider name reported by the composite model. */
|
|
897
|
+
provider?: string;
|
|
898
|
+
}
|
|
899
|
+
/**
|
|
900
|
+
* Composes several language models into one that tries each in order, falling
|
|
901
|
+
* back to the next when a model throws (subject to `shouldRetry`). Fallback
|
|
902
|
+
* applies to the initial `doGenerate` / `doStream` call; once a stream starts it
|
|
903
|
+
* is not switched mid-flight.
|
|
904
|
+
*
|
|
905
|
+
* @example
|
|
906
|
+
* ```ts
|
|
907
|
+
* const model = createFallbackModel([
|
|
908
|
+
* registry.getLanguageModel('openai:gpt-4o'),
|
|
909
|
+
* registry.getLanguageModel('anthropic:claude-sonnet-5'),
|
|
910
|
+
* ]);
|
|
911
|
+
* ```
|
|
912
|
+
*/
|
|
913
|
+
declare function createFallbackModel(models: LanguageModelV3[], options?: FallbackOptions): LanguageModelV3;
|
|
914
|
+
|
|
915
|
+
/**
|
|
916
|
+
* Default in-process cache with optional per-entry TTL. Not shared across
|
|
917
|
+
* processes — provide a distributed `AiCache` for production.
|
|
918
|
+
*/
|
|
919
|
+
declare class InMemoryAiCache implements AiCache {
|
|
920
|
+
private readonly store;
|
|
921
|
+
get(key: string): Promise<unknown | undefined>;
|
|
922
|
+
set(key: string, value: unknown, ttlMs?: number): Promise<void>;
|
|
923
|
+
}
|
|
924
|
+
|
|
925
|
+
interface CacheMiddlewareOptions {
|
|
926
|
+
/** Time-to-live for cached generations, in milliseconds (default: no expiry). */
|
|
927
|
+
ttlMs?: number;
|
|
928
|
+
}
|
|
929
|
+
/**
|
|
930
|
+
* Language-model middleware that caches non-streaming generations in an
|
|
931
|
+
* {@link AiCache}, keyed by the model id and call parameters. Wrap a model with
|
|
932
|
+
* `wrapLanguageModel({ model, middleware: createCacheMiddleware(cache) })`.
|
|
933
|
+
*/
|
|
934
|
+
declare function createCacheMiddleware(cache: AiCache, options?: CacheMiddlewareOptions): LanguageModelMiddleware;
|
|
935
|
+
/** Builds a stable cache key from the model id and call parameters. */
|
|
936
|
+
declare function cacheKey(modelId: string, params: unknown): string;
|
|
937
|
+
|
|
938
|
+
/** Default gate: approves every request. */
|
|
939
|
+
declare class AutoApproveGate implements ApprovalGate {
|
|
940
|
+
requestApproval(_context: ApprovalContext): Promise<boolean>;
|
|
941
|
+
}
|
|
942
|
+
/** Gate that denies every request (useful to hard-block approval tools). */
|
|
943
|
+
declare class DenyApproveGate implements ApprovalGate {
|
|
944
|
+
requestApproval(_context: ApprovalContext): Promise<boolean>;
|
|
945
|
+
}
|
|
946
|
+
|
|
947
|
+
interface AgentToolOptions {
|
|
948
|
+
/** Tool name exposed to the calling model (default: the agent class name). */
|
|
949
|
+
name?: string;
|
|
950
|
+
/** Description guiding when to delegate to this agent. */
|
|
951
|
+
description?: string;
|
|
952
|
+
/**
|
|
953
|
+
* Input schema. Defaults to `{ input: string }`; the `input` field is passed
|
|
954
|
+
* to the sub-agent's `.run()`.
|
|
955
|
+
*/
|
|
956
|
+
inputSchema?: ZodType<any, any, any>;
|
|
957
|
+
}
|
|
958
|
+
/**
|
|
959
|
+
* Wraps an agent as a tool so another agent can delegate to it (supervisor /
|
|
960
|
+
* handoff patterns). The wrapped agent's `.run()` output text is returned to the
|
|
961
|
+
* caller.
|
|
962
|
+
*
|
|
963
|
+
* @example
|
|
964
|
+
* ```ts
|
|
965
|
+
* @Agent({ model: 'openai:gpt-4o', system: 'Supervisor', tools: [ResearchAgent] })
|
|
966
|
+
* class SupervisorAgent extends AiAgent {}
|
|
967
|
+
* ```
|
|
968
|
+
*/
|
|
969
|
+
declare function createAgentTool(agent: Pick<AiAgent, 'run'>, options?: AgentToolOptions): Tool$1<any, string>;
|
|
970
|
+
|
|
971
|
+
/** Structural type for the pipe methods on a Vercel AI SDK stream result. */
|
|
972
|
+
interface PipeableStreamResult {
|
|
973
|
+
pipeUIMessageStreamToResponse?: (res: ServerResponse) => void;
|
|
974
|
+
pipeTextStreamToResponse?: (res: ServerResponse) => void;
|
|
975
|
+
}
|
|
976
|
+
interface PipeAgentStreamOptions {
|
|
977
|
+
/**
|
|
978
|
+
* Wire protocol: `'ui'` (AI SDK UI message stream, for `useChat`) or `'text'`
|
|
979
|
+
* (plain text stream). Defaults to `'ui'`.
|
|
980
|
+
*/
|
|
981
|
+
protocol?: 'ui' | 'text';
|
|
982
|
+
}
|
|
983
|
+
/**
|
|
984
|
+
* Pipes an agent/`AiService` stream result to an HTTP response (Express-style
|
|
985
|
+
* `ServerResponse`). Use in a controller that injected `@Res()`.
|
|
986
|
+
*
|
|
987
|
+
* @example
|
|
988
|
+
* ```ts
|
|
989
|
+
* @Post('chat')
|
|
990
|
+
* chat(@Body('prompt') prompt: string, @Res() res: Response) {
|
|
991
|
+
* pipeAgentStream(this.agent.stream(prompt), res, { protocol: 'ui' });
|
|
992
|
+
* }
|
|
993
|
+
* ```
|
|
994
|
+
*/
|
|
995
|
+
declare function pipeAgentStream(result: PipeableStreamResult, res: ServerResponse, options?: PipeAgentStreamOptions): void;
|
|
996
|
+
|
|
997
|
+
/**
|
|
998
|
+
* Interceptor that pipes a stream result returned by a route handler to the
|
|
999
|
+
* HTTP response. The handler returns the `streamText`/agent `.stream()` result;
|
|
1000
|
+
* the interceptor pipes it and completes the request.
|
|
1001
|
+
*
|
|
1002
|
+
* @example
|
|
1003
|
+
* ```ts
|
|
1004
|
+
* @UseInterceptors(new AgentStreamInterceptor({ protocol: 'ui' }))
|
|
1005
|
+
* @Post('chat')
|
|
1006
|
+
* chat(@Body('prompt') prompt: string) {
|
|
1007
|
+
* return this.agent.stream(prompt);
|
|
1008
|
+
* }
|
|
1009
|
+
* ```
|
|
1010
|
+
*/
|
|
1011
|
+
declare class AgentStreamInterceptor implements NestInterceptor {
|
|
1012
|
+
private readonly options;
|
|
1013
|
+
constructor(options?: PipeAgentStreamOptions);
|
|
1014
|
+
intercept(context: ExecutionContext, next: CallHandler): Observable<never>;
|
|
1015
|
+
}
|
|
1016
|
+
|
|
1017
|
+
/** A listed MCP tool (subset of the MCP `tools/list` result we use). */
|
|
1018
|
+
interface McpToolInfo {
|
|
1019
|
+
name: string;
|
|
1020
|
+
description?: string;
|
|
1021
|
+
inputSchema: unknown;
|
|
1022
|
+
}
|
|
1023
|
+
/** Result of an MCP `tools/call` (subset). */
|
|
1024
|
+
interface McpCallResult {
|
|
1025
|
+
content?: Array<{
|
|
1026
|
+
type: string;
|
|
1027
|
+
text?: string;
|
|
1028
|
+
[k: string]: unknown;
|
|
1029
|
+
}>;
|
|
1030
|
+
isError?: boolean;
|
|
1031
|
+
[k: string]: unknown;
|
|
1032
|
+
}
|
|
1033
|
+
/**
|
|
1034
|
+
* Structural interface for an MCP client (e.g. `Client` from
|
|
1035
|
+
* `@modelcontextprotocol/sdk`). Kept structural so this library has no
|
|
1036
|
+
* compile-time dependency on the SDK and can be tested with a fake.
|
|
1037
|
+
*/
|
|
1038
|
+
interface McpClientLike {
|
|
1039
|
+
listTools(): Promise<{
|
|
1040
|
+
tools: McpToolInfo[];
|
|
1041
|
+
}>;
|
|
1042
|
+
callTool(params: {
|
|
1043
|
+
name: string;
|
|
1044
|
+
arguments?: Record<string, unknown>;
|
|
1045
|
+
}): Promise<McpCallResult>;
|
|
1046
|
+
close?(): Promise<void>;
|
|
1047
|
+
}
|
|
1048
|
+
/**
|
|
1049
|
+
* Connects to MCP servers and adapts their tools into AI SDK tool sets that
|
|
1050
|
+
* agents can use. Register a connected client via `connect(name, client)`, then
|
|
1051
|
+
* reference its tools with `getToolSet(name)`.
|
|
1052
|
+
*/
|
|
1053
|
+
declare class McpService implements OnModuleDestroy {
|
|
1054
|
+
private readonly clients;
|
|
1055
|
+
private readonly toolSets;
|
|
1056
|
+
/**
|
|
1057
|
+
* Registers an MCP client under `name`, lists its tools, and builds a
|
|
1058
|
+
* matching AI SDK tool set. Returns the tool set.
|
|
1059
|
+
*/
|
|
1060
|
+
connect(name: string, client: McpClientLike): Promise<ToolSet>;
|
|
1061
|
+
/** Returns the tool set for a connected server (empty if unknown). */
|
|
1062
|
+
getToolSet(name: string): ToolSet;
|
|
1063
|
+
/** Returns tool sets for all connected servers, merged. */
|
|
1064
|
+
getAllTools(): ToolSet;
|
|
1065
|
+
onModuleDestroy(): Promise<void>;
|
|
1066
|
+
/** Closes every connected client. */
|
|
1067
|
+
closeAll(): Promise<void>;
|
|
1068
|
+
}
|
|
1069
|
+
|
|
1070
|
+
interface AgentJobsOptions {
|
|
1071
|
+
/** BullMQ connection (ioredis connection or options). */
|
|
1072
|
+
connection: unknown;
|
|
1073
|
+
/** Queue name (default `"ai-agent-runs"`). */
|
|
1074
|
+
queueName?: string;
|
|
1075
|
+
/** Start a worker in this process to consume jobs (default `true`). */
|
|
1076
|
+
runWorker?: boolean;
|
|
1077
|
+
}
|
|
1078
|
+
/**
|
|
1079
|
+
* Background-job module for asynchronous agent execution on BullMQ. Import it
|
|
1080
|
+
* where you need it (it is separate from the global `AiModule`).
|
|
1081
|
+
*
|
|
1082
|
+
* @example
|
|
1083
|
+
* ```ts
|
|
1084
|
+
* AgentJobsModule.forRoot({ connection: { host: 'localhost', port: 6379 } })
|
|
1085
|
+
* ```
|
|
1086
|
+
* Requires the optional peers `bullmq` (and typically a Redis instance).
|
|
1087
|
+
*/
|
|
1088
|
+
declare class AgentJobsModule {
|
|
1089
|
+
static forRoot(options: AgentJobsOptions): DynamicModule;
|
|
1090
|
+
}
|
|
1091
|
+
|
|
1092
|
+
/** Payload of a queued agent run. */
|
|
1093
|
+
interface AgentJobData {
|
|
1094
|
+
/** Agent class name (as indexed by `AgentRegistry`). */
|
|
1095
|
+
agent: string;
|
|
1096
|
+
/** Input passed to the agent's `.run()`. */
|
|
1097
|
+
input: AiInput;
|
|
1098
|
+
/** Per-call run options. */
|
|
1099
|
+
options?: AgentRunOptions;
|
|
1100
|
+
}
|
|
1101
|
+
/** Minimal structural interface for a BullMQ-like queue. */
|
|
1102
|
+
interface QueueLike {
|
|
1103
|
+
add(name: string, data: AgentJobData, opts?: Record<string, unknown>): Promise<{
|
|
1104
|
+
id?: string;
|
|
1105
|
+
}>;
|
|
1106
|
+
}
|
|
1107
|
+
|
|
1108
|
+
/** The job name used for queued agent runs. */
|
|
1109
|
+
declare const AGENT_JOB_NAME = "agent-run";
|
|
1110
|
+
/**
|
|
1111
|
+
* Enqueues agent runs onto a BullMQ queue for asynchronous processing. The
|
|
1112
|
+
* queue is injected under the `AGENT_QUEUE` token by `AgentJobsModule`.
|
|
1113
|
+
*/
|
|
1114
|
+
declare class AgentQueueService {
|
|
1115
|
+
private readonly queue;
|
|
1116
|
+
constructor(queue: QueueLike);
|
|
1117
|
+
/** Enqueues an agent run and returns the created job id. */
|
|
1118
|
+
enqueue(data: AgentJobData, jobOptions?: Record<string, unknown>): Promise<string | undefined>;
|
|
1119
|
+
}
|
|
1120
|
+
|
|
1121
|
+
/**
|
|
1122
|
+
* Runs a queued agent job by resolving the agent from the {@link AgentRegistry}
|
|
1123
|
+
* and invoking its `.run()`. Framework-agnostic: a BullMQ worker simply calls
|
|
1124
|
+
* `run(job.data)`.
|
|
1125
|
+
*/
|
|
1126
|
+
declare class AgentJobProcessor {
|
|
1127
|
+
private readonly agents;
|
|
1128
|
+
constructor(agents: AgentRegistry);
|
|
1129
|
+
run(data: AgentJobData): Promise<AgentResult>;
|
|
1130
|
+
}
|
|
1131
|
+
|
|
1132
|
+
/** Structural interface for a `pg` Pool/Client (only `query` is used). */
|
|
1133
|
+
interface PgPoolLike {
|
|
1134
|
+
query(sql: string, params?: unknown[]): Promise<{
|
|
1135
|
+
rows: Array<Record<string, any>>;
|
|
1136
|
+
}>;
|
|
1137
|
+
}
|
|
1138
|
+
interface PgVectorStoreOptions {
|
|
1139
|
+
/** Table name (default `"ai_documents"`). */
|
|
1140
|
+
table?: string;
|
|
1141
|
+
}
|
|
1142
|
+
/**
|
|
1143
|
+
* `VectorStore` backed by Postgres + the `pgvector` extension. Pass a `pg`
|
|
1144
|
+
* `Pool` (or any object with a compatible `query`). Expects a table like:
|
|
1145
|
+
*
|
|
1146
|
+
* ```sql
|
|
1147
|
+
* CREATE EXTENSION IF NOT EXISTS vector;
|
|
1148
|
+
* CREATE TABLE ai_documents (
|
|
1149
|
+
* id text PRIMARY KEY,
|
|
1150
|
+
* content text NOT NULL,
|
|
1151
|
+
* embedding vector(1536) NOT NULL,
|
|
1152
|
+
* metadata jsonb
|
|
1153
|
+
* );
|
|
1154
|
+
* CREATE INDEX ON ai_documents USING hnsw (embedding vector_cosine_ops);
|
|
1155
|
+
* ```
|
|
1156
|
+
*/
|
|
1157
|
+
declare class PgVectorStore implements VectorStore {
|
|
1158
|
+
private readonly pool;
|
|
1159
|
+
private readonly table;
|
|
1160
|
+
constructor(pool: PgPoolLike, options?: PgVectorStoreOptions);
|
|
1161
|
+
upsert(documents: VectorDocument[]): Promise<void>;
|
|
1162
|
+
query(embedding: number[], options?: VectorQueryOptions): Promise<VectorQueryResult[]>;
|
|
1163
|
+
delete(ids: string[]): Promise<void>;
|
|
1164
|
+
clear(): Promise<void>;
|
|
1165
|
+
}
|
|
1166
|
+
|
|
1167
|
+
/** Thrown when a conversation exceeds its configured cost budget. */
|
|
1168
|
+
declare class BudgetExceededError extends Error {
|
|
1169
|
+
readonly conversationId: string | undefined;
|
|
1170
|
+
readonly spent: number;
|
|
1171
|
+
readonly limit: number;
|
|
1172
|
+
constructor(conversationId: string | undefined, spent: number, limit: number);
|
|
1173
|
+
}
|
|
1174
|
+
/**
|
|
1175
|
+
* Guardrail that blocks a run when the conversation's accumulated cost has
|
|
1176
|
+
* reached `maxCostPerConversation`. Registered automatically when that option
|
|
1177
|
+
* is set.
|
|
1178
|
+
*/
|
|
1179
|
+
declare class BudgetGuard implements Guardrail$1 {
|
|
1180
|
+
private readonly usage;
|
|
1181
|
+
private readonly options;
|
|
1182
|
+
constructor(usage: UsageTracker, options: AiModuleOptions);
|
|
1183
|
+
beforeRun(ctx: GuardrailContext): void;
|
|
1184
|
+
}
|
|
1185
|
+
|
|
1186
|
+
/**
|
|
1187
|
+
* Throttles agent runs. Implement this (e.g. Redis) for distributed limiting
|
|
1188
|
+
* and register it via `AiModule.forRoot({ rateLimiter })`.
|
|
1189
|
+
*/
|
|
1190
|
+
interface RateLimiter {
|
|
1191
|
+
/**
|
|
1192
|
+
* Attempts to consume `cost` units for `key`. Resolves `true` if allowed,
|
|
1193
|
+
* `false` if the limit is exceeded.
|
|
1194
|
+
*/
|
|
1195
|
+
consume(key: string, cost?: number): Promise<boolean>;
|
|
1196
|
+
}
|
|
1197
|
+
/** Thrown by the rate-limit guardrail when a run is throttled. */
|
|
1198
|
+
declare class RateLimitedError extends Error {
|
|
1199
|
+
readonly key: string;
|
|
1200
|
+
constructor(key: string);
|
|
1201
|
+
}
|
|
1202
|
+
|
|
1203
|
+
interface InMemoryRateLimiterOptions {
|
|
1204
|
+
/** Maximum tokens in the bucket (burst size). */
|
|
1205
|
+
capacity: number;
|
|
1206
|
+
/** Tokens added per `intervalMs`. */
|
|
1207
|
+
refillTokens: number;
|
|
1208
|
+
/** Refill interval in milliseconds. */
|
|
1209
|
+
intervalMs: number;
|
|
1210
|
+
/** Clock, for testing. Defaults to `Date.now`. */
|
|
1211
|
+
now?: () => number;
|
|
1212
|
+
}
|
|
1213
|
+
/**
|
|
1214
|
+
* In-process token-bucket rate limiter, keyed (e.g. by conversation or user).
|
|
1215
|
+
* Not shared across processes — provide a distributed `RateLimiter` for scale.
|
|
1216
|
+
*/
|
|
1217
|
+
declare class InMemoryRateLimiter implements RateLimiter {
|
|
1218
|
+
private readonly options;
|
|
1219
|
+
private readonly buckets;
|
|
1220
|
+
private readonly now;
|
|
1221
|
+
constructor(options: InMemoryRateLimiterOptions);
|
|
1222
|
+
consume(key: string, cost?: number): Promise<boolean>;
|
|
1223
|
+
}
|
|
1224
|
+
|
|
1225
|
+
/**
|
|
1226
|
+
* Guardrail that throttles runs through the configured `RateLimiter`, keyed by
|
|
1227
|
+
* conversation id (or `"global"`). Registered when `rateLimiter` is set.
|
|
1228
|
+
*/
|
|
1229
|
+
declare class RateLimitGuardrail implements Guardrail$1 {
|
|
1230
|
+
private readonly limiter;
|
|
1231
|
+
constructor(limiter: RateLimiter);
|
|
1232
|
+
beforeRun(ctx: GuardrailContext): Promise<void>;
|
|
1233
|
+
}
|
|
1234
|
+
|
|
1235
|
+
/** Default PII regexes: email, phone, credit card, US SSN. */
|
|
1236
|
+
declare const DEFAULT_PII_PATTERNS: RegExp[];
|
|
1237
|
+
interface PiiRedactionOptions {
|
|
1238
|
+
patterns?: RegExp[];
|
|
1239
|
+
replacement?: string;
|
|
1240
|
+
}
|
|
1241
|
+
/** Redacts PII matches in a string. */
|
|
1242
|
+
declare function redactPii(text: string, patterns?: RegExp[], replacement?: string): string;
|
|
1243
|
+
/** Redacts PII in every message's textual content, in place. */
|
|
1244
|
+
declare function redactMessages(messages: AiMessage[], patterns?: RegExp[], replacement?: string): void;
|
|
1245
|
+
/**
|
|
1246
|
+
* Guardrail that redacts PII in the messages sent to the model (default
|
|
1247
|
+
* patterns). For custom patterns use {@link createPiiRedactionGuardrail}.
|
|
1248
|
+
*/
|
|
1249
|
+
declare class PiiRedactionGuardrail implements Guardrail$1 {
|
|
1250
|
+
beforeRun(ctx: GuardrailContext): void;
|
|
1251
|
+
}
|
|
1252
|
+
/** Builds a configured PII-redaction guardrail class (discoverable via DI). */
|
|
1253
|
+
declare function createPiiRedactionGuardrail(options?: PiiRedactionOptions): Type<Guardrail$1>;
|
|
1254
|
+
|
|
1255
|
+
/** Thrown when moderation blocks content. */
|
|
1256
|
+
declare class ContentBlockedError extends Error {
|
|
1257
|
+
readonly reason: string;
|
|
1258
|
+
constructor(reason: string);
|
|
1259
|
+
}
|
|
1260
|
+
interface ModerationOptions {
|
|
1261
|
+
/** Case-insensitive terms that block a run when present. */
|
|
1262
|
+
blocked?: string[];
|
|
1263
|
+
/**
|
|
1264
|
+
* Optional async check returning `true` to block. Runs in addition to the
|
|
1265
|
+
* deny-list (e.g. call a provider moderation endpoint).
|
|
1266
|
+
*/
|
|
1267
|
+
moderate?: (text: string) => boolean | Promise<boolean>;
|
|
1268
|
+
}
|
|
1269
|
+
/**
|
|
1270
|
+
* Builds a moderation guardrail that blocks runs whose input contains a
|
|
1271
|
+
* deny-listed term or fails a custom `moderate` check.
|
|
1272
|
+
*/
|
|
1273
|
+
declare function createModerationGuardrail(options?: ModerationOptions): Type<Guardrail$1>;
|
|
1274
|
+
|
|
1275
|
+
interface HeuristicRerankerOptions {
|
|
1276
|
+
/** Weight of the query-term overlap boost relative to the base score. */
|
|
1277
|
+
overlapWeight?: number;
|
|
1278
|
+
}
|
|
1279
|
+
/**
|
|
1280
|
+
* Zero-dependency reranker that boosts results whose content shares terms with
|
|
1281
|
+
* the query, on top of the base similarity score. A pragmatic default when no
|
|
1282
|
+
* reranking model is configured.
|
|
1283
|
+
*/
|
|
1284
|
+
declare class HeuristicReranker implements Reranker {
|
|
1285
|
+
private readonly options;
|
|
1286
|
+
constructor(options?: HeuristicRerankerOptions);
|
|
1287
|
+
rerank(query: string, results: VectorQueryResult[], topN: number): Promise<VectorQueryResult[]>;
|
|
1288
|
+
}
|
|
1289
|
+
|
|
1290
|
+
/**
|
|
1291
|
+
* Reranker backed by a provider reranking model via the AI SDK's `rerank()`.
|
|
1292
|
+
* Requires a rerank-capable provider (e.g. `@ai-sdk/cohere`) configured through
|
|
1293
|
+
* `rerankingModel`.
|
|
1294
|
+
*/
|
|
1295
|
+
declare class ModelReranker implements Reranker {
|
|
1296
|
+
private readonly providers;
|
|
1297
|
+
private readonly model?;
|
|
1298
|
+
constructor(providers: ProviderRegistry, model?: string | undefined);
|
|
1299
|
+
rerank(query: string, results: VectorQueryResult[], topN: number): Promise<VectorQueryResult[]>;
|
|
1300
|
+
}
|
|
1301
|
+
|
|
1302
|
+
/** Structural subset of the Qdrant JS client we use. */
|
|
1303
|
+
interface QdrantClientLike {
|
|
1304
|
+
upsert(collection: string, params: unknown): Promise<unknown>;
|
|
1305
|
+
search(collection: string, params: unknown): Promise<Array<{
|
|
1306
|
+
id: string | number;
|
|
1307
|
+
score: number;
|
|
1308
|
+
payload?: any;
|
|
1309
|
+
}>>;
|
|
1310
|
+
delete(collection: string, params: unknown): Promise<unknown>;
|
|
1311
|
+
}
|
|
1312
|
+
interface QdrantVectorStoreOptions {
|
|
1313
|
+
collection: string;
|
|
1314
|
+
}
|
|
1315
|
+
/**
|
|
1316
|
+
* `VectorStore` backed by Qdrant. Pass a `@qdrant/js-client-rest` `QdrantClient`
|
|
1317
|
+
* (or a compatible object). The payload stores `content` alongside metadata.
|
|
1318
|
+
*/
|
|
1319
|
+
declare class QdrantVectorStore implements VectorStore {
|
|
1320
|
+
private readonly client;
|
|
1321
|
+
private readonly options;
|
|
1322
|
+
constructor(client: QdrantClientLike, options: QdrantVectorStoreOptions);
|
|
1323
|
+
upsert(documents: VectorDocument[]): Promise<void>;
|
|
1324
|
+
query(embedding: number[], options?: VectorQueryOptions): Promise<VectorQueryResult[]>;
|
|
1325
|
+
delete(ids: string[]): Promise<void>;
|
|
1326
|
+
clear(): Promise<void>;
|
|
1327
|
+
}
|
|
1328
|
+
|
|
1329
|
+
/** Structural subset of a Pinecone index (namespace) we use. */
|
|
1330
|
+
interface PineconeIndexLike {
|
|
1331
|
+
upsert(vectors: Array<{
|
|
1332
|
+
id: string;
|
|
1333
|
+
values: number[];
|
|
1334
|
+
metadata?: any;
|
|
1335
|
+
}>): Promise<unknown>;
|
|
1336
|
+
query(params: {
|
|
1337
|
+
vector: number[];
|
|
1338
|
+
topK: number;
|
|
1339
|
+
includeMetadata?: boolean;
|
|
1340
|
+
filter?: Record<string, unknown>;
|
|
1341
|
+
}): Promise<{
|
|
1342
|
+
matches?: Array<{
|
|
1343
|
+
id: string;
|
|
1344
|
+
score?: number;
|
|
1345
|
+
metadata?: any;
|
|
1346
|
+
}>;
|
|
1347
|
+
}>;
|
|
1348
|
+
deleteMany(ids: string[]): Promise<unknown>;
|
|
1349
|
+
deleteAll(): Promise<unknown>;
|
|
1350
|
+
}
|
|
1351
|
+
/**
|
|
1352
|
+
* `VectorStore` backed by Pinecone. Pass a Pinecone index (optionally scoped to
|
|
1353
|
+
* a namespace): `pinecone.index('name').namespace('ns')`. `content` is stored in
|
|
1354
|
+
* the vector metadata.
|
|
1355
|
+
*/
|
|
1356
|
+
declare class PineconeVectorStore implements VectorStore {
|
|
1357
|
+
private readonly index;
|
|
1358
|
+
constructor(index: PineconeIndexLike);
|
|
1359
|
+
upsert(documents: VectorDocument[]): Promise<void>;
|
|
1360
|
+
query(embedding: number[], options?: VectorQueryOptions): Promise<VectorQueryResult[]>;
|
|
1361
|
+
delete(ids: string[]): Promise<void>;
|
|
1362
|
+
clear(): Promise<void>;
|
|
1363
|
+
}
|
|
1364
|
+
|
|
1365
|
+
/** A single evaluation case. */
|
|
1366
|
+
interface EvalCase {
|
|
1367
|
+
name?: string;
|
|
1368
|
+
input: string;
|
|
1369
|
+
/** Expected substring/answer (used by the default judge). */
|
|
1370
|
+
expected?: string;
|
|
1371
|
+
/** Rubric text passed to an LLM judge. */
|
|
1372
|
+
rubric?: string;
|
|
1373
|
+
}
|
|
1374
|
+
/** A judge's verdict for one output. */
|
|
1375
|
+
interface EvalScore {
|
|
1376
|
+
/** Normalized score in [0, 1]. */
|
|
1377
|
+
score: number;
|
|
1378
|
+
passed: boolean;
|
|
1379
|
+
reasoning?: string;
|
|
1380
|
+
}
|
|
1381
|
+
/** Full result for one case. */
|
|
1382
|
+
interface EvalResult extends EvalScore {
|
|
1383
|
+
name: string;
|
|
1384
|
+
input: string;
|
|
1385
|
+
output: string;
|
|
1386
|
+
}
|
|
1387
|
+
/** Aggregate report over all cases. */
|
|
1388
|
+
interface EvalReport {
|
|
1389
|
+
results: EvalResult[];
|
|
1390
|
+
averageScore: number;
|
|
1391
|
+
passRate: number;
|
|
1392
|
+
}
|
|
1393
|
+
/** Scores an agent output against its case. */
|
|
1394
|
+
type Judge = (ctx: {
|
|
1395
|
+
case: EvalCase;
|
|
1396
|
+
output: string;
|
|
1397
|
+
}) => Promise<EvalScore> | EvalScore;
|
|
1398
|
+
|
|
1399
|
+
/** Minimal agent shape the runner needs. */
|
|
1400
|
+
interface RunnableAgent {
|
|
1401
|
+
run(input: string): Promise<{
|
|
1402
|
+
text: string;
|
|
1403
|
+
}>;
|
|
1404
|
+
}
|
|
1405
|
+
/** Minimal `AiService` shape for the LLM judge. */
|
|
1406
|
+
interface JudgeAi {
|
|
1407
|
+
generateObject(params: {
|
|
1408
|
+
model?: string;
|
|
1409
|
+
schema: unknown;
|
|
1410
|
+
prompt: string;
|
|
1411
|
+
}): Promise<{
|
|
1412
|
+
object: {
|
|
1413
|
+
score: number;
|
|
1414
|
+
reasoning: string;
|
|
1415
|
+
};
|
|
1416
|
+
}>;
|
|
1417
|
+
}
|
|
1418
|
+
interface RunEvalOptions {
|
|
1419
|
+
judge?: Judge;
|
|
1420
|
+
/** Pass threshold in [0, 1] for the default judge (default 1). */
|
|
1421
|
+
passThreshold?: number;
|
|
1422
|
+
}
|
|
1423
|
+
/**
|
|
1424
|
+
* Runs an agent over a set of cases and scores each output with a judge
|
|
1425
|
+
* (default: substring match against `expected`; or an LLM judge).
|
|
1426
|
+
*/
|
|
1427
|
+
declare class EvalRunner {
|
|
1428
|
+
run(agent: RunnableAgent, cases: EvalCase[], options?: RunEvalOptions): Promise<EvalReport>;
|
|
1429
|
+
}
|
|
1430
|
+
/** Substring-match judge against `case.expected`. */
|
|
1431
|
+
declare function defaultJudge(threshold: number): Judge;
|
|
1432
|
+
/**
|
|
1433
|
+
* Builds an LLM-as-judge that scores outputs 0..`scale` and normalizes to [0,1].
|
|
1434
|
+
*/
|
|
1435
|
+
declare function createLlmJudge(ai: JudgeAi, options?: {
|
|
1436
|
+
model?: string;
|
|
1437
|
+
scale?: number;
|
|
1438
|
+
passThreshold?: number;
|
|
1439
|
+
}): Judge;
|
|
1440
|
+
|
|
1441
|
+
export { AGENT_JOB_NAME, AGENT_QUEUE, AI_CACHE, AI_EVENTS, AI_MODULE_OPTIONS, APPROVAL_GATE, Agent, AgentExecutorService, type AgentJobData, AgentJobProcessor, AgentJobsModule, type AgentJobsOptions, type AgentOptions, AgentQueueService, AgentRegistry, type AgentResult, type AgentRunErrorPayload, type AgentRunFinishPayload, type AgentRunOptions, type AgentRunStartPayload, AgentStreamInterceptor, type AgentToolOptions, AiAgent, type AiCache, AiEventEmitter, AiFeatureOptions, AiInput, AiMessage, AiModule, AiModuleAsyncOptions, AiModuleOptions, AiService, type ApprovalContext, type ApprovalGate, type AudioInput, AutoApproveGate, BudgetExceededError, BudgetGuard, CONVERSATION_STORE, type CacheMiddlewareOptions, ContentBlockedError, ConversationStore, DEFAULT_MAX_STEPS, DEFAULT_PII_PATTERNS, DenyApproveGate, EVENT_EMITTER, type EmbedOptions, EmbeddingsService, type EvalCase, type EvalReport, type EvalResult, EvalRunner, type EvalScore, type EventEmitterLike, type FallbackOptions, type GenerateImageOptions, type GenerateSpeechOptions, Guardrail, type GuardrailContext, type Guardrail$1 as GuardrailContract, GuardrailRegistry, HeuristicReranker, type HeuristicRerankerOptions, ImageService, InMemoryAiCache, InMemoryConversationStore, InMemoryRateLimiter, type InMemoryRateLimiterOptions, InMemoryVectorStore, type IngestItem, type IngestOptions, type Judge, type JudgeAi, type McpCallResult, type McpClientLike, McpService, type McpToolInfo, ModelReranker, type ModerationOptions, type PgPoolLike, PgVectorStore, type PgVectorStoreOptions, PiiRedactionGuardrail, type PiiRedactionOptions, type PineconeIndexLike, PineconeVectorStore, type PipeAgentStreamOptions, type PipeableStreamResult, type PrismaConversationDelegate, PrismaConversationStore, PromptDefinition, PromptRef, PromptRegistry, ProviderRegistry, type QdrantClientLike, QdrantVectorStore, type QdrantVectorStoreOptions, type QueueLike, RATE_LIMITER, RERANKER, RagService, RateLimitGuardrail, RateLimitedError, type RateLimiter, type RecallOptions, type Reranker, type RetrievalToolOptions, type RetrieveOptions, type RunEvalOptions, type RunnableAgent, SemanticMemory, SpeechService, Tool, ToolApprovalDeniedError, type ToolCallPayload, type ToolEntry, type ToolMetadata, type ToolOptions, type ToolRef, ToolRegistry, type ToolResultPayload, type TranscribeOptions, TranscriptionService, type UsageRecord, type UsageTotals, UsageTracker, VECTOR_STORE, type VectorDocument, type VectorQueryOptions, type VectorQueryResult, type VectorStore, cacheKey, createAgentTool, createCacheMiddleware, createFallbackModel, createLlmJudge, createModerationGuardrail, createPiiRedactionGuardrail, createRetrievalTool, defaultJudge, pipeAgentStream, redactMessages, redactPii, splitText };
|