@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.
Files changed (50) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +655 -0
  3. package/dist/ai-module-options.interface-B5X4AFLC.d.cts +192 -0
  4. package/dist/ai-module-options.interface-Ca6y_MY2.d.ts +192 -0
  5. package/dist/conversation-store.interface-CtQY-qcc.d.cts +30 -0
  6. package/dist/conversation-store.interface-CtQY-qcc.d.ts +30 -0
  7. package/dist/index.cjs +3209 -0
  8. package/dist/index.cjs.map +1 -0
  9. package/dist/index.d.cts +1441 -0
  10. package/dist/index.d.ts +1441 -0
  11. package/dist/index.js +3163 -0
  12. package/dist/index.js.map +1 -0
  13. package/dist/stream-to-socket-fJphU0WN.d.cts +47 -0
  14. package/dist/stream-to-socket-fJphU0WN.d.ts +47 -0
  15. package/dist/testing.cjs +2395 -0
  16. package/dist/testing.cjs.map +1 -0
  17. package/dist/testing.d.cts +46 -0
  18. package/dist/testing.d.ts +46 -0
  19. package/dist/testing.js +2391 -0
  20. package/dist/testing.js.map +1 -0
  21. package/dist/typeorm.cjs +115 -0
  22. package/dist/typeorm.cjs.map +1 -0
  23. package/dist/typeorm.d.cts +44 -0
  24. package/dist/typeorm.d.ts +44 -0
  25. package/dist/typeorm.js +113 -0
  26. package/dist/typeorm.js.map +1 -0
  27. package/dist/websocket.cjs +154 -0
  28. package/dist/websocket.cjs.map +1 -0
  29. package/dist/websocket.d.cts +25 -0
  30. package/dist/websocket.d.ts +25 -0
  31. package/dist/websocket.js +152 -0
  32. package/dist/websocket.js.map +1 -0
  33. package/documentation/README.md +44 -0
  34. package/documentation/agents-and-tools.md +102 -0
  35. package/documentation/api-reference.md +117 -0
  36. package/documentation/configuration.md +87 -0
  37. package/documentation/content-safety.md +51 -0
  38. package/documentation/embeddings-and-rag.md +105 -0
  39. package/documentation/evals-and-testing.md +56 -0
  40. package/documentation/getting-started.md +96 -0
  41. package/documentation/guardrails-events-telemetry.md +72 -0
  42. package/documentation/jobs-and-realtime.md +69 -0
  43. package/documentation/memory.md +101 -0
  44. package/documentation/multimodal.md +49 -0
  45. package/documentation/orchestration-and-mcp.md +68 -0
  46. package/documentation/prompts.md +51 -0
  47. package/documentation/reliability.md +90 -0
  48. package/documentation/structured-output-and-streaming.md +81 -0
  49. package/package.json +146 -0
  50. package/skill/nestjs-ai/SKILL.md +154 -0
@@ -0,0 +1,2391 @@
1
+ import { MockLanguageModelV3, MockEmbeddingModelV3 } from 'ai/test';
2
+ import { Test } from '@nestjs/testing';
3
+ import { Injectable, Inject, Optional, Global, Module } from '@nestjs/common';
4
+ import { DiscoveryService, MetadataScanner, Reflector, DiscoveryModule, ModuleRef } from '@nestjs/core';
5
+ import { wrapLanguageModel, tool, generateText, streamText, generateObject, streamObject, embed, embedMany, stepCountIs, generateImage, experimental_generateSpeech, experimental_transcribe, cosineSimilarity, dynamicTool, jsonSchema } from 'ai';
6
+ import { z } from 'zod';
7
+ import 'reflect-metadata';
8
+
9
+ var __defProp = Object.defineProperty;
10
+ var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
11
+ var ZERO_USAGE = {
12
+ inputTokens: 0,
13
+ outputTokens: 0,
14
+ totalTokens: 0
15
+ };
16
+ function createMockModel(replies) {
17
+ const texts = Array.isArray(replies) ? replies : [
18
+ replies
19
+ ];
20
+ const results = texts.map((text) => ({
21
+ content: [
22
+ {
23
+ type: "text",
24
+ text
25
+ }
26
+ ],
27
+ finishReason: "stop",
28
+ usage: ZERO_USAGE,
29
+ warnings: []
30
+ }));
31
+ let call = 0;
32
+ return new MockLanguageModelV3({
33
+ doGenerate: /* @__PURE__ */ __name(async () => results[Math.min(call++, results.length - 1)], "doGenerate")
34
+ });
35
+ }
36
+ __name(createMockModel, "createMockModel");
37
+ function createEmbeddingMock(embed2) {
38
+ return new MockEmbeddingModelV3({
39
+ doEmbed: /* @__PURE__ */ __name(async ({ values }) => ({
40
+ embeddings: values.map(embed2),
41
+ usage: {
42
+ tokens: values.length
43
+ }
44
+ }), "doEmbed")
45
+ });
46
+ }
47
+ __name(createEmbeddingMock, "createEmbeddingMock");
48
+
49
+ // src/ai.constants.ts
50
+ var AI_MODULE_OPTIONS = /* @__PURE__ */ Symbol("AI_MODULE_OPTIONS");
51
+ var CONVERSATION_STORE = /* @__PURE__ */ Symbol("CONVERSATION_STORE");
52
+ var VECTOR_STORE = /* @__PURE__ */ Symbol("VECTOR_STORE");
53
+ var AI_CACHE = /* @__PURE__ */ Symbol("AI_CACHE");
54
+ var APPROVAL_GATE = /* @__PURE__ */ Symbol("APPROVAL_GATE");
55
+ var RATE_LIMITER = /* @__PURE__ */ Symbol("RATE_LIMITER");
56
+ var RERANKER = /* @__PURE__ */ Symbol("RERANKER");
57
+ var TOOL_METADATA = /* @__PURE__ */ Symbol("nestjs-ai:tool");
58
+ var AGENT_METADATA = /* @__PURE__ */ Symbol("nestjs-ai:agent");
59
+ var GUARDRAIL_METADATA = /* @__PURE__ */ Symbol("nestjs-ai:guardrail");
60
+ var DEFAULT_MAX_STEPS = 5;
61
+
62
+ // src/resilience/fallback-model.ts
63
+ function createFallbackModel(models, options = {}) {
64
+ if (models.length === 0) {
65
+ throw new Error("createFallbackModel requires at least one model.");
66
+ }
67
+ const primary = models[0];
68
+ const shouldRetry = options.shouldRetry ?? (() => true);
69
+ async function attempt(call) {
70
+ let lastError;
71
+ for (let i = 0; i < models.length; i++) {
72
+ try {
73
+ return await call(models[i]);
74
+ } catch (error) {
75
+ lastError = error;
76
+ const isLast = i === models.length - 1;
77
+ if (isLast || !shouldRetry(error)) {
78
+ throw error;
79
+ }
80
+ }
81
+ }
82
+ throw lastError;
83
+ }
84
+ __name(attempt, "attempt");
85
+ return {
86
+ specificationVersion: "v3",
87
+ provider: options.provider ?? `fallback(${primary.provider})`,
88
+ modelId: primary.modelId,
89
+ get supportedUrls() {
90
+ return primary.supportedUrls;
91
+ },
92
+ doGenerate: /* @__PURE__ */ __name((callOptions) => attempt((model) => model.doGenerate(callOptions)), "doGenerate"),
93
+ doStream: /* @__PURE__ */ __name((callOptions) => attempt((model) => model.doStream(callOptions)), "doStream")
94
+ };
95
+ }
96
+ __name(createFallbackModel, "createFallbackModel");
97
+
98
+ // src/cache/cache-middleware.ts
99
+ function createCacheMiddleware(cache, options = {}) {
100
+ return {
101
+ async wrapGenerate({ doGenerate, params, model }) {
102
+ const key = cacheKey(model.modelId, params);
103
+ const cached = await cache.get(key);
104
+ if (cached !== void 0) {
105
+ return cached;
106
+ }
107
+ const result = await doGenerate();
108
+ await cache.set(key, result, options.ttlMs);
109
+ return result;
110
+ }
111
+ };
112
+ }
113
+ __name(createCacheMiddleware, "createCacheMiddleware");
114
+ function cacheKey(modelId, params) {
115
+ return `${modelId}:${stableStringify(params)}`;
116
+ }
117
+ __name(cacheKey, "cacheKey");
118
+ function stableStringify(value) {
119
+ return JSON.stringify(value, (_key, val) => {
120
+ if (val && typeof val === "object" && !Array.isArray(val)) {
121
+ return Object.keys(val).sort().reduce((acc, k) => {
122
+ acc[k] = val[k];
123
+ return acc;
124
+ }, {});
125
+ }
126
+ return val;
127
+ });
128
+ }
129
+ __name(stableStringify, "stableStringify");
130
+
131
+ // src/core/provider-registry.ts
132
+ function _ts_decorate(decorators, target, key, desc) {
133
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
134
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
135
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
136
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
137
+ }
138
+ __name(_ts_decorate, "_ts_decorate");
139
+ function _ts_metadata(k, v) {
140
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
141
+ }
142
+ __name(_ts_metadata, "_ts_metadata");
143
+ function _ts_param(paramIndex, decorator) {
144
+ return function(target, key) {
145
+ decorator(target, key, paramIndex);
146
+ };
147
+ }
148
+ __name(_ts_param, "_ts_param");
149
+ var ProviderRegistry = class {
150
+ static {
151
+ __name(this, "ProviderRegistry");
152
+ }
153
+ options;
154
+ cache;
155
+ providers = /* @__PURE__ */ new Map();
156
+ constructor(options, cache) {
157
+ this.options = options;
158
+ this.cache = cache;
159
+ }
160
+ /** Wraps a model with the cache middleware when a cache is configured. */
161
+ applyCache(model) {
162
+ if (!this.cache || typeof model === "string") {
163
+ return model;
164
+ }
165
+ return wrapLanguageModel({
166
+ model,
167
+ middleware: createCacheMiddleware(this.cache, {
168
+ ttlMs: this.options.cacheTtlMs
169
+ })
170
+ });
171
+ }
172
+ async onModuleInit() {
173
+ const configured = this.options.providers ?? {};
174
+ for (const name of Object.keys(configured)) {
175
+ const config = configured[name];
176
+ if (config) {
177
+ await this.initProvider(name, config);
178
+ }
179
+ }
180
+ }
181
+ /**
182
+ * Resolves a language model. Accepts a `LanguageModel` instance (returned
183
+ * as-is), a `"provider:model"` string, a bare `"model"` string (using the
184
+ * default provider), or `undefined` (using `defaultModel`).
185
+ */
186
+ getLanguageModel(model) {
187
+ const chain = model ?? this.options.defaultModel;
188
+ if (Array.isArray(chain)) {
189
+ if (chain.length === 0) {
190
+ throw new Error("An empty model array was provided.");
191
+ }
192
+ if (chain.length === 1) {
193
+ return this.getLanguageModel(chain[0]);
194
+ }
195
+ const resolved = chain.map((m) => this.resolveSingle(m));
196
+ return this.applyCache(createFallbackModel(resolved));
197
+ }
198
+ return this.applyCache(this.resolveSingle(chain));
199
+ }
200
+ /** Resolves a single (non-array) model reference without cache wrapping. */
201
+ resolveSingle(model) {
202
+ if (model && typeof model !== "string") {
203
+ return model;
204
+ }
205
+ const { provider, modelId } = this.resolve(model, void 0);
206
+ return provider.languageModel(modelId);
207
+ }
208
+ /**
209
+ * Resolves an embedding model from a `"provider:model"` string, a bare model
210
+ * string, an `EmbeddingModel` instance, or `undefined` (using
211
+ * `defaultEmbeddingModel`).
212
+ */
213
+ getEmbeddingModel(model) {
214
+ if (model && typeof model !== "string") {
215
+ return model;
216
+ }
217
+ const { name, provider, modelId } = this.resolve(model, this.options.defaultEmbeddingModel);
218
+ if (typeof provider.textEmbeddingModel !== "function") {
219
+ throw new Error(`Provider "${name}" does not support embeddings. Configure a provider with embedding support (e.g. openai or google).`);
220
+ }
221
+ return provider.textEmbeddingModel(modelId);
222
+ }
223
+ /** Resolves an image-generation model (default `defaultImageModel`). */
224
+ getImageModel(model) {
225
+ if (model && typeof model !== "string") {
226
+ return model;
227
+ }
228
+ return this.resolveMultimodal(model, this.options.defaultImageModel, [
229
+ "imageModel",
230
+ "image"
231
+ ], "image generation");
232
+ }
233
+ /** Resolves a reranking model (default `rerankingModel` option). */
234
+ getRerankingModel(model) {
235
+ if (model && typeof model !== "string") {
236
+ return model;
237
+ }
238
+ return this.resolveMultimodal(model, this.options.rerankingModel, [
239
+ "rerankingModel",
240
+ "reranking"
241
+ ], "reranking");
242
+ }
243
+ /** Resolves a speech (text-to-speech) model (default `defaultSpeechModel`). */
244
+ getSpeechModel(model) {
245
+ if (model && typeof model !== "string") {
246
+ return model;
247
+ }
248
+ return this.resolveMultimodal(model, this.options.defaultSpeechModel, [
249
+ "speechModel",
250
+ "speech"
251
+ ], "speech");
252
+ }
253
+ /** Resolves a transcription (speech-to-text) model. */
254
+ getTranscriptionModel(model) {
255
+ if (model && typeof model !== "string") {
256
+ return model;
257
+ }
258
+ return this.resolveMultimodal(model, this.options.defaultTranscriptionModel, [
259
+ "transcriptionModel",
260
+ "transcription"
261
+ ], "transcription");
262
+ }
263
+ /**
264
+ * Shared resolution for multimodal models: resolves the provider, then calls
265
+ * the first available factory method (standard name, then shorthand).
266
+ */
267
+ resolveMultimodal(model, fallback, methods, capability) {
268
+ const { name, provider, modelId } = this.resolve(model, fallback);
269
+ for (const method of methods) {
270
+ const fn = provider[method];
271
+ if (typeof fn === "function") {
272
+ return fn.call(provider, modelId);
273
+ }
274
+ }
275
+ throw new Error(`Provider "${name}" does not support ${capability}. Configure a provider that does (e.g. openai).`);
276
+ }
277
+ resolve(model, fallback) {
278
+ const raw = model ?? fallback;
279
+ if (!raw) {
280
+ throw new Error("No model specified and no default model configured. Pass a model id or set `defaultModel` in AiModule options.");
281
+ }
282
+ const name = this.parseProviderName(raw);
283
+ const modelId = this.parseModelId(raw);
284
+ const provider = this.providers.get(name);
285
+ if (!provider) {
286
+ throw new Error(`Provider "${name}" is not configured. Add it to AiModule \`providers\` options and install \`@ai-sdk/${name}\`.`);
287
+ }
288
+ return {
289
+ name,
290
+ provider,
291
+ modelId
292
+ };
293
+ }
294
+ parseProviderName(raw) {
295
+ const sep = raw.indexOf(":");
296
+ if (sep !== -1) {
297
+ return raw.slice(0, sep);
298
+ }
299
+ if (this.providers.size === 1) {
300
+ return this.providers.keys().next().value;
301
+ }
302
+ const def = this.options.defaultModel;
303
+ if (def && def.includes(":")) {
304
+ return def.slice(0, def.indexOf(":"));
305
+ }
306
+ throw new Error(`Cannot infer provider for model "${raw}". Prefix it as "provider:model" (e.g. "openai:${raw}").`);
307
+ }
308
+ parseModelId(raw) {
309
+ const sep = raw.indexOf(":");
310
+ return sep !== -1 ? raw.slice(sep + 1) : raw;
311
+ }
312
+ async initProvider(name, config) {
313
+ const settings = {
314
+ apiKey: config.apiKey,
315
+ baseURL: config.baseURL,
316
+ headers: config.headers
317
+ };
318
+ try {
319
+ switch (name) {
320
+ case "openai": {
321
+ const { createOpenAI } = await import('@ai-sdk/openai');
322
+ this.providers.set(name, createOpenAI(settings));
323
+ break;
324
+ }
325
+ case "anthropic": {
326
+ const { createAnthropic } = await import('@ai-sdk/anthropic');
327
+ this.providers.set(name, createAnthropic(settings));
328
+ break;
329
+ }
330
+ case "google": {
331
+ const { createGoogleGenerativeAI } = await import('@ai-sdk/google');
332
+ this.providers.set(name, createGoogleGenerativeAI(settings));
333
+ break;
334
+ }
335
+ default: {
336
+ throw new Error(`Unknown provider "${name}".`);
337
+ }
338
+ }
339
+ } catch (error) {
340
+ if (error instanceof Error && /Cannot find|find module/i.test(error.message)) {
341
+ throw new Error(`Provider "${name}" is configured but the package "@ai-sdk/${name}" is not installed. Run \`npm install @ai-sdk/${name}\`.`);
342
+ }
343
+ throw error;
344
+ }
345
+ }
346
+ };
347
+ ProviderRegistry = _ts_decorate([
348
+ Injectable(),
349
+ _ts_param(0, Inject(AI_MODULE_OPTIONS)),
350
+ _ts_param(1, Optional()),
351
+ _ts_param(1, Inject(AI_CACHE)),
352
+ _ts_metadata("design:type", Function),
353
+ _ts_metadata("design:paramtypes", [
354
+ typeof AiModuleOptions === "undefined" ? Object : AiModuleOptions,
355
+ typeof AiCache === "undefined" ? Object : AiCache
356
+ ])
357
+ ], ProviderRegistry);
358
+ function _ts_decorate2(decorators, target, key, desc) {
359
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
360
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
361
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
362
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
363
+ }
364
+ __name(_ts_decorate2, "_ts_decorate");
365
+ function _ts_metadata2(k, v) {
366
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
367
+ }
368
+ __name(_ts_metadata2, "_ts_metadata");
369
+ function _ts_param2(paramIndex, decorator) {
370
+ return function(target, key) {
371
+ decorator(target, key, paramIndex);
372
+ };
373
+ }
374
+ __name(_ts_param2, "_ts_param");
375
+ var EVENT_EMITTER = /* @__PURE__ */ Symbol("AI_EVENT_EMITTER");
376
+ var AiEventEmitter = class {
377
+ static {
378
+ __name(this, "AiEventEmitter");
379
+ }
380
+ emitter;
381
+ constructor(emitter) {
382
+ this.emitter = emitter;
383
+ }
384
+ emit(event, payload) {
385
+ this.emitter?.emit(event, payload);
386
+ }
387
+ /** Whether an underlying emitter is wired up. */
388
+ get enabled() {
389
+ return this.emitter != null;
390
+ }
391
+ };
392
+ AiEventEmitter = _ts_decorate2([
393
+ Injectable(),
394
+ _ts_param2(0, Optional()),
395
+ _ts_param2(0, Inject(EVENT_EMITTER)),
396
+ _ts_metadata2("design:type", Function),
397
+ _ts_metadata2("design:paramtypes", [
398
+ Object
399
+ ])
400
+ ], AiEventEmitter);
401
+
402
+ // src/observability/ai-events.ts
403
+ var AI_EVENTS = {
404
+ agentRunStart: "ai.agent.run.start",
405
+ agentRunFinish: "ai.agent.run.finish",
406
+ agentRunError: "ai.agent.run.error",
407
+ toolCall: "ai.tool.call",
408
+ toolResult: "ai.tool.result",
409
+ streamFinish: "ai.stream.finish",
410
+ usage: "ai.usage"
411
+ };
412
+ function _ts_decorate3(decorators, target, key, desc) {
413
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
414
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
415
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
416
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
417
+ }
418
+ __name(_ts_decorate3, "_ts_decorate");
419
+ function _ts_metadata3(k, v) {
420
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
421
+ }
422
+ __name(_ts_metadata3, "_ts_metadata");
423
+ var GuardrailRegistry = class {
424
+ static {
425
+ __name(this, "GuardrailRegistry");
426
+ }
427
+ discovery;
428
+ guardrails = [];
429
+ constructor(discovery) {
430
+ this.discovery = discovery;
431
+ }
432
+ onModuleInit() {
433
+ for (const wrapper of this.discovery.getProviders()) {
434
+ const instance = wrapper.instance;
435
+ const ctor = instance?.constructor;
436
+ if (instance && ctor && Reflect.getMetadata(GUARDRAIL_METADATA, ctor) === true) {
437
+ this.guardrails.push(instance);
438
+ }
439
+ }
440
+ }
441
+ get count() {
442
+ return this.guardrails.length;
443
+ }
444
+ async runBeforeRun(ctx) {
445
+ for (const guardrail of this.guardrails) {
446
+ await guardrail.beforeRun?.(ctx);
447
+ }
448
+ }
449
+ async runAfterRun(ctx, result) {
450
+ for (const guardrail of this.guardrails) {
451
+ await guardrail.afterRun?.(ctx, result);
452
+ }
453
+ }
454
+ async runOnToolCall(tool3, args) {
455
+ for (const guardrail of this.guardrails) {
456
+ await guardrail.onToolCall?.(tool3, args);
457
+ }
458
+ }
459
+ };
460
+ GuardrailRegistry = _ts_decorate3([
461
+ Injectable(),
462
+ _ts_metadata3("design:type", Function),
463
+ _ts_metadata3("design:paramtypes", [
464
+ typeof DiscoveryService === "undefined" ? Object : DiscoveryService
465
+ ])
466
+ ], GuardrailRegistry);
467
+ function _ts_decorate4(decorators, target, key, desc) {
468
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
469
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
470
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
471
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
472
+ }
473
+ __name(_ts_decorate4, "_ts_decorate");
474
+ function _ts_metadata4(k, v) {
475
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
476
+ }
477
+ __name(_ts_metadata4, "_ts_metadata");
478
+ var AgentRegistry = class {
479
+ static {
480
+ __name(this, "AgentRegistry");
481
+ }
482
+ discovery;
483
+ agents = /* @__PURE__ */ new Map();
484
+ constructor(discovery) {
485
+ this.discovery = discovery;
486
+ }
487
+ onModuleInit() {
488
+ for (const wrapper of this.discovery.getProviders()) {
489
+ const instance = wrapper.instance;
490
+ const ctor = instance?.constructor;
491
+ if (instance && ctor && Reflect.getMetadata(AGENT_METADATA, ctor)) {
492
+ this.agents.set(ctor.name, {
493
+ name: ctor.name,
494
+ instance,
495
+ target: ctor
496
+ });
497
+ }
498
+ }
499
+ }
500
+ /** Returns an agent instance by class name. */
501
+ get(name) {
502
+ return this.agents.get(name)?.instance;
503
+ }
504
+ /** Returns an agent instance by its class. */
505
+ getByClass(target) {
506
+ return this.agents.get(target.name)?.instance;
507
+ }
508
+ /** All discovered agents. */
509
+ all() {
510
+ return [
511
+ ...this.agents.values()
512
+ ];
513
+ }
514
+ };
515
+ AgentRegistry = _ts_decorate4([
516
+ Injectable(),
517
+ _ts_metadata4("design:type", Function),
518
+ _ts_metadata4("design:paramtypes", [
519
+ typeof DiscoveryService === "undefined" ? Object : DiscoveryService
520
+ ])
521
+ ], AgentRegistry);
522
+ function createAgentTool(agent, options = {}) {
523
+ const schema = options.inputSchema ?? z.object({
524
+ input: z.string().describe("The task or question for the agent")
525
+ });
526
+ return tool({
527
+ description: options.description ?? `Delegate the task to the ${options.name ?? "sub"} agent.`,
528
+ inputSchema: schema,
529
+ execute: /* @__PURE__ */ __name(async (args) => {
530
+ const input = typeof args === "string" ? args : args?.input ?? JSON.stringify(args);
531
+ const result = await agent.run(input);
532
+ return result.text;
533
+ }, "execute")
534
+ });
535
+ }
536
+ __name(createAgentTool, "createAgentTool");
537
+
538
+ // src/approval/approval-gate.interface.ts
539
+ var ToolApprovalDeniedError = class extends Error {
540
+ static {
541
+ __name(this, "ToolApprovalDeniedError");
542
+ }
543
+ tool;
544
+ constructor(tool3) {
545
+ super(`Tool "${tool3}" was denied by the approval gate.`), this.tool = tool3;
546
+ this.name = "ToolApprovalDeniedError";
547
+ }
548
+ };
549
+
550
+ // src/tools/tool.registry.ts
551
+ function _ts_decorate5(decorators, target, key, desc) {
552
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
553
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
554
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
555
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
556
+ }
557
+ __name(_ts_decorate5, "_ts_decorate");
558
+ function _ts_metadata5(k, v) {
559
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
560
+ }
561
+ __name(_ts_metadata5, "_ts_metadata");
562
+ function _ts_param3(paramIndex, decorator) {
563
+ return function(target, key) {
564
+ decorator(target, key, paramIndex);
565
+ };
566
+ }
567
+ __name(_ts_param3, "_ts_param");
568
+ var ToolRegistry = class {
569
+ static {
570
+ __name(this, "ToolRegistry");
571
+ }
572
+ discovery;
573
+ scanner;
574
+ reflector;
575
+ events;
576
+ guardrails;
577
+ approvalGate;
578
+ agentRegistry;
579
+ tools = /* @__PURE__ */ new Map();
580
+ constructor(discovery, scanner, reflector, events, guardrails, approvalGate, agentRegistry) {
581
+ this.discovery = discovery;
582
+ this.scanner = scanner;
583
+ this.reflector = reflector;
584
+ this.events = events;
585
+ this.guardrails = guardrails;
586
+ this.approvalGate = approvalGate;
587
+ this.agentRegistry = agentRegistry;
588
+ }
589
+ onModuleInit() {
590
+ for (const wrapper of this.discovery.getProviders()) {
591
+ const instance = wrapper.instance;
592
+ if (!instance || typeof instance !== "object") {
593
+ continue;
594
+ }
595
+ const prototype = Object.getPrototypeOf(instance);
596
+ if (!prototype) {
597
+ continue;
598
+ }
599
+ for (const methodName of this.scanner.getAllMethodNames(prototype)) {
600
+ const methodRef = instance[methodName];
601
+ const metadata = this.reflector.get(TOOL_METADATA, methodRef);
602
+ if (!metadata) {
603
+ continue;
604
+ }
605
+ this.register(instance, methodName, metadata);
606
+ }
607
+ }
608
+ }
609
+ register(instance, methodName, metadata) {
610
+ const name = metadata.name ?? methodName;
611
+ if (this.tools.has(name)) {
612
+ throw new Error(`Duplicate AI tool name "${name}". Tool names must be unique across all providers (declared on ${instance.constructor?.name}).`);
613
+ }
614
+ const built = tool({
615
+ description: metadata.description,
616
+ inputSchema: metadata.schema,
617
+ execute: /* @__PURE__ */ __name(async (args, opts) => {
618
+ if (metadata.requiresApproval && this.approvalGate) {
619
+ const approved = await this.approvalGate.requestApproval({
620
+ tool: name,
621
+ args
622
+ });
623
+ if (!approved) {
624
+ throw new ToolApprovalDeniedError(name);
625
+ }
626
+ }
627
+ await this.guardrails?.runOnToolCall(name, args);
628
+ this.events?.emit(AI_EVENTS.toolCall, {
629
+ tool: name,
630
+ args
631
+ });
632
+ const result = await instance[methodName](args, opts);
633
+ this.events?.emit(AI_EVENTS.toolResult, {
634
+ tool: name,
635
+ args,
636
+ result
637
+ });
638
+ return result;
639
+ }, "execute")
640
+ });
641
+ this.tools.set(name, {
642
+ name,
643
+ tool: built,
644
+ target: instance.constructor
645
+ });
646
+ }
647
+ /** Returns the tool registered under `name`, if any. */
648
+ getByName(name) {
649
+ return this.tools.get(name);
650
+ }
651
+ /** Returns every tool declared by the given provider class. */
652
+ getForClass(target) {
653
+ return [
654
+ ...this.tools.values()
655
+ ].filter((entry) => entry.target === target);
656
+ }
657
+ /** Returns all discovered tools. */
658
+ getAll() {
659
+ return [
660
+ ...this.tools.values()
661
+ ];
662
+ }
663
+ /**
664
+ * Builds the `ToolSet` passed to `generateText`/`streamText` from a list of
665
+ * tool references (provider classes and/or tool names). Passing no refs
666
+ * returns every discovered tool.
667
+ */
668
+ buildToolSet(refs) {
669
+ const entries = refs && refs.length > 0 ? refs.flatMap((ref) => this.resolveRef(ref)) : this.getAll();
670
+ const set = {};
671
+ for (const entry of entries) {
672
+ set[entry.name] = entry.tool;
673
+ }
674
+ return set;
675
+ }
676
+ resolveRef(ref) {
677
+ if (typeof ref === "string") {
678
+ const entry = this.getByName(ref);
679
+ if (!entry) {
680
+ throw new Error(`Unknown AI tool "${ref}".`);
681
+ }
682
+ return [
683
+ entry
684
+ ];
685
+ }
686
+ const entries = this.getForClass(ref);
687
+ if (entries.length > 0) {
688
+ return entries;
689
+ }
690
+ const agentEntry = this.resolveAgentRef(ref);
691
+ if (agentEntry) {
692
+ return [
693
+ agentEntry
694
+ ];
695
+ }
696
+ throw new Error(`Class "${ref.name}" declares no @Tool methods and is not a registered @Agent, or was not registered as a provider so it could be discovered.`);
697
+ }
698
+ resolveAgentRef(ref) {
699
+ if (!this.agentRegistry || !Reflect.getMetadata(AGENT_METADATA, ref)) {
700
+ return void 0;
701
+ }
702
+ const instance = this.agentRegistry.getByClass(ref);
703
+ if (!instance) {
704
+ return void 0;
705
+ }
706
+ return {
707
+ name: ref.name,
708
+ tool: createAgentTool(instance, {
709
+ name: ref.name
710
+ }),
711
+ target: ref
712
+ };
713
+ }
714
+ };
715
+ ToolRegistry = _ts_decorate5([
716
+ Injectable(),
717
+ _ts_param3(3, Optional()),
718
+ _ts_param3(4, Optional()),
719
+ _ts_param3(5, Optional()),
720
+ _ts_param3(5, Inject(APPROVAL_GATE)),
721
+ _ts_param3(6, Optional()),
722
+ _ts_metadata5("design:type", Function),
723
+ _ts_metadata5("design:paramtypes", [
724
+ typeof DiscoveryService === "undefined" ? Object : DiscoveryService,
725
+ typeof MetadataScanner === "undefined" ? Object : MetadataScanner,
726
+ typeof Reflector === "undefined" ? Object : Reflector,
727
+ typeof AiEventEmitter === "undefined" ? Object : AiEventEmitter,
728
+ typeof GuardrailRegistry === "undefined" ? Object : GuardrailRegistry,
729
+ typeof ApprovalGate === "undefined" ? Object : ApprovalGate,
730
+ typeof AgentRegistry === "undefined" ? Object : AgentRegistry
731
+ ])
732
+ ], ToolRegistry);
733
+
734
+ // src/core/ai.service.ts
735
+ function _ts_decorate6(decorators, target, key, desc) {
736
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
737
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
738
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
739
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
740
+ }
741
+ __name(_ts_decorate6, "_ts_decorate");
742
+ function _ts_metadata6(k, v) {
743
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
744
+ }
745
+ __name(_ts_metadata6, "_ts_metadata");
746
+ var AiService = class {
747
+ static {
748
+ __name(this, "AiService");
749
+ }
750
+ providers;
751
+ toolRegistry;
752
+ constructor(providers, toolRegistry) {
753
+ this.providers = providers;
754
+ this.toolRegistry = toolRegistry;
755
+ }
756
+ generateText(params) {
757
+ return generateText(this.resolve(params));
758
+ }
759
+ streamText(params) {
760
+ return streamText(this.resolve(params));
761
+ }
762
+ generateObject(params) {
763
+ return generateObject(this.resolve(params));
764
+ }
765
+ streamObject(params) {
766
+ return streamObject(this.resolve(params));
767
+ }
768
+ resolve(params) {
769
+ const { model, tools, ...rest } = params;
770
+ return {
771
+ ...rest,
772
+ model: this.providers.getLanguageModel(model),
773
+ ...tools ? {
774
+ tools: this.toolRegistry.buildToolSet(tools)
775
+ } : {}
776
+ };
777
+ }
778
+ };
779
+ AiService = _ts_decorate6([
780
+ Injectable(),
781
+ _ts_metadata6("design:type", Function),
782
+ _ts_metadata6("design:paramtypes", [
783
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry,
784
+ typeof ToolRegistry === "undefined" ? Object : ToolRegistry
785
+ ])
786
+ ], AiService);
787
+
788
+ // src/messages/message.types.ts
789
+ function toMessages(input) {
790
+ if (typeof input === "string") {
791
+ return [
792
+ {
793
+ role: "user",
794
+ content: input
795
+ }
796
+ ];
797
+ }
798
+ return input;
799
+ }
800
+ __name(toMessages, "toMessages");
801
+
802
+ // src/prompts/prompt.types.ts
803
+ var PLACEHOLDER = /\{\{\s*([\w.]+)\s*\}\}/g;
804
+ function interpolate(template, vars = {}) {
805
+ return template.replace(PLACEHOLDER, (_match, key) => {
806
+ if (!(key in vars)) {
807
+ throw new Error(`Missing variable "${key}" for prompt interpolation.`);
808
+ }
809
+ const value = vars[key];
810
+ return value == null ? "" : String(value);
811
+ });
812
+ }
813
+ __name(interpolate, "interpolate");
814
+
815
+ // src/prompts/prompt-registry.service.ts
816
+ function _ts_decorate7(decorators, target, key, desc) {
817
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
818
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
819
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
820
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
821
+ }
822
+ __name(_ts_decorate7, "_ts_decorate");
823
+ var DEFAULT_VERSION = "__default__";
824
+ var PromptRegistry = class {
825
+ static {
826
+ __name(this, "PromptRegistry");
827
+ }
828
+ /** name -> (version -> definition) */
829
+ prompts = /* @__PURE__ */ new Map();
830
+ /** name -> most recently registered version key */
831
+ latest = /* @__PURE__ */ new Map();
832
+ /** Registers a prompt. Throws on a duplicate (name, version). */
833
+ register(definition) {
834
+ const versions = this.prompts.get(definition.name) ?? /* @__PURE__ */ new Map();
835
+ const versionKey = definition.version ?? DEFAULT_VERSION;
836
+ if (versions.has(versionKey)) {
837
+ throw new Error(`Prompt "${definition.name}"${definition.version ? ` version "${definition.version}"` : ""} is already registered.`);
838
+ }
839
+ versions.set(versionKey, definition);
840
+ this.prompts.set(definition.name, versions);
841
+ this.latest.set(definition.name, versionKey);
842
+ }
843
+ /** Registers many prompts. */
844
+ registerAll(definitions) {
845
+ for (const definition of definitions) {
846
+ this.register(definition);
847
+ }
848
+ }
849
+ /** Returns a prompt definition (latest version when `version` omitted). */
850
+ get(name, version) {
851
+ const versions = this.prompts.get(name);
852
+ if (!versions) {
853
+ throw new Error(`Unknown prompt "${name}".`);
854
+ }
855
+ const versionKey = version ?? this.latest.get(name) ?? DEFAULT_VERSION;
856
+ const definition = versions.get(versionKey);
857
+ if (!definition) {
858
+ throw new Error(`Unknown version "${version}" for prompt "${name}".`);
859
+ }
860
+ return definition;
861
+ }
862
+ /** Renders a prompt to a string, interpolating `{{var}}` placeholders. */
863
+ render(name, vars = {}, options = {}) {
864
+ return interpolate(this.get(name, options.version).template, vars);
865
+ }
866
+ /** Whether a prompt (any version) is registered. */
867
+ has(name) {
868
+ return this.prompts.has(name);
869
+ }
870
+ };
871
+ PromptRegistry = _ts_decorate7([
872
+ Injectable()
873
+ ], PromptRegistry);
874
+
875
+ // src/usage/pricing.ts
876
+ var DEFAULT_PRICING = {
877
+ "gpt-4o": {
878
+ input: 2.5,
879
+ output: 10
880
+ },
881
+ "gpt-4o-mini": {
882
+ input: 0.15,
883
+ output: 0.6
884
+ },
885
+ "gpt-4.1": {
886
+ input: 2,
887
+ output: 8
888
+ },
889
+ "gpt-4.1-mini": {
890
+ input: 0.4,
891
+ output: 1.6
892
+ },
893
+ "o3-mini": {
894
+ input: 1.1,
895
+ output: 4.4
896
+ },
897
+ "text-embedding-3-small": {
898
+ input: 0.02,
899
+ output: 0
900
+ },
901
+ "text-embedding-3-large": {
902
+ input: 0.13,
903
+ output: 0
904
+ },
905
+ "claude-sonnet-4": {
906
+ input: 3,
907
+ output: 15
908
+ },
909
+ "claude-opus-4": {
910
+ input: 15,
911
+ output: 75
912
+ },
913
+ "claude-haiku-4": {
914
+ input: 0.8,
915
+ output: 4
916
+ },
917
+ "gemini-2.5-pro": {
918
+ input: 1.25,
919
+ output: 10
920
+ },
921
+ "gemini-2.5-flash": {
922
+ input: 0.3,
923
+ output: 2.5
924
+ }
925
+ };
926
+ function bareModelId(modelId) {
927
+ const sep = modelId.indexOf(":");
928
+ return sep === -1 ? modelId : modelId.slice(sep + 1);
929
+ }
930
+ __name(bareModelId, "bareModelId");
931
+ function costOf(usage, modelId, pricing = DEFAULT_PRICING) {
932
+ const price = pricing[bareModelId(modelId)] ?? pricing[modelId];
933
+ if (!price) {
934
+ return 0;
935
+ }
936
+ const input = usage.inputTokens ?? 0;
937
+ const output = usage.outputTokens ?? 0;
938
+ return input / 1e6 * price.input + output / 1e6 * price.output;
939
+ }
940
+ __name(costOf, "costOf");
941
+
942
+ // src/usage/usage-tracker.service.ts
943
+ function _ts_decorate8(decorators, target, key, desc) {
944
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
945
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
946
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
947
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
948
+ }
949
+ __name(_ts_decorate8, "_ts_decorate");
950
+ function _ts_metadata7(k, v) {
951
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
952
+ }
953
+ __name(_ts_metadata7, "_ts_metadata");
954
+ function _ts_param4(paramIndex, decorator) {
955
+ return function(target, key) {
956
+ decorator(target, key, paramIndex);
957
+ };
958
+ }
959
+ __name(_ts_param4, "_ts_param");
960
+ var GLOBAL = "__global__";
961
+ function empty() {
962
+ return {
963
+ inputTokens: 0,
964
+ outputTokens: 0,
965
+ cost: 0,
966
+ runs: 0
967
+ };
968
+ }
969
+ __name(empty, "empty");
970
+ var UsageTracker = class {
971
+ static {
972
+ __name(this, "UsageTracker");
973
+ }
974
+ options;
975
+ events;
976
+ totalsByScope = /* @__PURE__ */ new Map();
977
+ constructor(options, events) {
978
+ this.options = options;
979
+ this.events = events;
980
+ }
981
+ /** Records a run's usage, returns the single-run record, emits `ai.usage`. */
982
+ record(entry) {
983
+ const usage = entry.usage ?? {};
984
+ const inputTokens = usage.inputTokens ?? 0;
985
+ const outputTokens = usage.outputTokens ?? 0;
986
+ const cost = costOf(usage, entry.model, this.options.pricing);
987
+ for (const scope of [
988
+ GLOBAL,
989
+ entry.conversationId
990
+ ].filter(Boolean)) {
991
+ const totals = this.totalsByScope.get(scope) ?? empty();
992
+ totals.inputTokens += inputTokens;
993
+ totals.outputTokens += outputTokens;
994
+ totals.cost += cost;
995
+ totals.runs += 1;
996
+ this.totalsByScope.set(scope, totals);
997
+ }
998
+ const record = {
999
+ conversationId: entry.conversationId,
1000
+ agent: entry.agent,
1001
+ model: entry.model,
1002
+ inputTokens,
1003
+ outputTokens,
1004
+ cost,
1005
+ runs: 1
1006
+ };
1007
+ this.events?.emit(AI_EVENTS.usage, record);
1008
+ return record;
1009
+ }
1010
+ /** Totals for a conversation, or global totals when no id is given. */
1011
+ totals(conversationId) {
1012
+ return {
1013
+ ...this.totalsByScope.get(conversationId ?? GLOBAL) ?? empty()
1014
+ };
1015
+ }
1016
+ /** Clears totals for a conversation (or all when no id). */
1017
+ reset(conversationId) {
1018
+ if (conversationId) {
1019
+ this.totalsByScope.delete(conversationId);
1020
+ } else {
1021
+ this.totalsByScope.clear();
1022
+ }
1023
+ }
1024
+ };
1025
+ UsageTracker = _ts_decorate8([
1026
+ Injectable(),
1027
+ _ts_param4(0, Inject(AI_MODULE_OPTIONS)),
1028
+ _ts_param4(1, Optional()),
1029
+ _ts_metadata7("design:type", Function),
1030
+ _ts_metadata7("design:paramtypes", [
1031
+ typeof AiModuleOptions === "undefined" ? Object : AiModuleOptions,
1032
+ typeof AiEventEmitter === "undefined" ? Object : AiEventEmitter
1033
+ ])
1034
+ ], UsageTracker);
1035
+ function _ts_decorate9(decorators, target, key, desc) {
1036
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1037
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1038
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1039
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1040
+ }
1041
+ __name(_ts_decorate9, "_ts_decorate");
1042
+ function _ts_metadata8(k, v) {
1043
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1044
+ }
1045
+ __name(_ts_metadata8, "_ts_metadata");
1046
+ function _ts_param5(paramIndex, decorator) {
1047
+ return function(target, key) {
1048
+ decorator(target, key, paramIndex);
1049
+ };
1050
+ }
1051
+ __name(_ts_param5, "_ts_param");
1052
+ var EmbeddingsService = class {
1053
+ static {
1054
+ __name(this, "EmbeddingsService");
1055
+ }
1056
+ providers;
1057
+ cache;
1058
+ constructor(providers, cache) {
1059
+ this.providers = providers;
1060
+ this.cache = cache;
1061
+ }
1062
+ /** Embeds a single value (cached when a cache is configured). */
1063
+ async embed(value, options = {}) {
1064
+ const model = this.providers.getEmbeddingModel(options.model);
1065
+ const key = `emb:${model.modelId ?? ""}:${value}`;
1066
+ if (this.cache) {
1067
+ const hit = await this.cache.get(key);
1068
+ if (hit !== void 0) {
1069
+ return hit;
1070
+ }
1071
+ }
1072
+ const result = await embed({
1073
+ model,
1074
+ value,
1075
+ abortSignal: options.abortSignal,
1076
+ maxRetries: options.maxRetries
1077
+ });
1078
+ if (this.cache) {
1079
+ await this.cache.set(key, result);
1080
+ }
1081
+ return result;
1082
+ }
1083
+ /** Embeds many values (the SDK batches automatically). */
1084
+ async embedMany(values, options = {}) {
1085
+ return embedMany({
1086
+ model: this.providers.getEmbeddingModel(options.model),
1087
+ values,
1088
+ abortSignal: options.abortSignal,
1089
+ maxRetries: options.maxRetries
1090
+ });
1091
+ }
1092
+ };
1093
+ EmbeddingsService = _ts_decorate9([
1094
+ Injectable(),
1095
+ _ts_param5(1, Optional()),
1096
+ _ts_param5(1, Inject(AI_CACHE)),
1097
+ _ts_metadata8("design:type", Function),
1098
+ _ts_metadata8("design:paramtypes", [
1099
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry,
1100
+ typeof AiCache === "undefined" ? Object : AiCache
1101
+ ])
1102
+ ], EmbeddingsService);
1103
+
1104
+ // src/memory/semantic/semantic-memory.service.ts
1105
+ function _ts_decorate10(decorators, target, key, desc) {
1106
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1107
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1108
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1109
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1110
+ }
1111
+ __name(_ts_decorate10, "_ts_decorate");
1112
+ function _ts_metadata9(k, v) {
1113
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1114
+ }
1115
+ __name(_ts_metadata9, "_ts_metadata");
1116
+ function _ts_param6(paramIndex, decorator) {
1117
+ return function(target, key) {
1118
+ decorator(target, key, paramIndex);
1119
+ };
1120
+ }
1121
+ __name(_ts_param6, "_ts_param");
1122
+ var SemanticMemory = class {
1123
+ static {
1124
+ __name(this, "SemanticMemory");
1125
+ }
1126
+ embeddings;
1127
+ store;
1128
+ ai;
1129
+ constructor(embeddings, store, ai) {
1130
+ this.embeddings = embeddings;
1131
+ this.store = store;
1132
+ this.ai = ai;
1133
+ }
1134
+ /** Embeds and stores a snippet under a conversation. */
1135
+ async remember(conversationId, text, options = {}) {
1136
+ const { embedding } = await this.embeddings.embed(text, {
1137
+ model: options.model
1138
+ });
1139
+ await this.store.upsert([
1140
+ {
1141
+ id: `mem:${conversationId}:${hash(text)}`,
1142
+ content: text,
1143
+ embedding,
1144
+ metadata: {
1145
+ conversationId,
1146
+ kind: "memory",
1147
+ ...options.metadata
1148
+ }
1149
+ }
1150
+ ]);
1151
+ }
1152
+ /** Returns the most relevant stored snippets for a query. */
1153
+ async recall(conversationId, query, options = {}) {
1154
+ const { embedding } = await this.embeddings.embed(query, {
1155
+ model: options.model
1156
+ });
1157
+ return this.store.query(embedding, {
1158
+ topK: options.topK ?? 4,
1159
+ filter: {
1160
+ conversationId,
1161
+ kind: "memory"
1162
+ }
1163
+ });
1164
+ }
1165
+ /**
1166
+ * Summarizes messages with the LLM (requires `AiService`), then stores the
1167
+ * summary as a memory snippet. Returns the stored text.
1168
+ */
1169
+ async rememberConversation(conversationId, input, options = {}) {
1170
+ const text = options.summarize ? await this.summarize(input, options.model) : messagesToText(input);
1171
+ await this.remember(conversationId, text, {
1172
+ model: options.model
1173
+ });
1174
+ return text;
1175
+ }
1176
+ /** Summarizes messages into a compact string via the LLM. */
1177
+ async summarize(input, model) {
1178
+ if (!this.ai) {
1179
+ throw new Error("SemanticMemory.summarize requires AiService.");
1180
+ }
1181
+ const { text } = await this.ai.generateText({
1182
+ model,
1183
+ prompt: `Summarize the following conversation concisely:
1184
+
1185
+ ${messagesToText(input)}`
1186
+ });
1187
+ return text;
1188
+ }
1189
+ };
1190
+ SemanticMemory = _ts_decorate10([
1191
+ Injectable(),
1192
+ _ts_param6(1, Inject(VECTOR_STORE)),
1193
+ _ts_param6(2, Optional()),
1194
+ _ts_metadata9("design:type", Function),
1195
+ _ts_metadata9("design:paramtypes", [
1196
+ typeof EmbeddingsService === "undefined" ? Object : EmbeddingsService,
1197
+ typeof VectorStore === "undefined" ? Object : VectorStore,
1198
+ typeof AiService === "undefined" ? Object : AiService
1199
+ ])
1200
+ ], SemanticMemory);
1201
+ function messagesToText(input) {
1202
+ return toMessages(input).map((m) => {
1203
+ const content = m.content;
1204
+ if (typeof content === "string") {
1205
+ return `${m.role}: ${content}`;
1206
+ }
1207
+ if (Array.isArray(content)) {
1208
+ return `${m.role}: ${content.map((p) => p && typeof p.text === "string" ? p.text : "").join(" ")}`;
1209
+ }
1210
+ return "";
1211
+ }).join("\n");
1212
+ }
1213
+ __name(messagesToText, "messagesToText");
1214
+ function hash(text) {
1215
+ let h = 5381;
1216
+ for (let i = 0; i < text.length; i++) {
1217
+ h = h * 33 ^ text.charCodeAt(i);
1218
+ }
1219
+ return (h >>> 0).toString(36);
1220
+ }
1221
+ __name(hash, "hash");
1222
+
1223
+ // src/agent/agent-executor.service.ts
1224
+ function _ts_decorate11(decorators, target, key, desc) {
1225
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1226
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1227
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1228
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1229
+ }
1230
+ __name(_ts_decorate11, "_ts_decorate");
1231
+ function _ts_metadata10(k, v) {
1232
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1233
+ }
1234
+ __name(_ts_metadata10, "_ts_metadata");
1235
+ function _ts_param7(paramIndex, decorator) {
1236
+ return function(target, key) {
1237
+ decorator(target, key, paramIndex);
1238
+ };
1239
+ }
1240
+ __name(_ts_param7, "_ts_param");
1241
+ var AgentExecutorService = class {
1242
+ static {
1243
+ __name(this, "AgentExecutorService");
1244
+ }
1245
+ providers;
1246
+ toolRegistry;
1247
+ store;
1248
+ options;
1249
+ events;
1250
+ guardrails;
1251
+ prompts;
1252
+ usageTracker;
1253
+ semanticMemory;
1254
+ constructor(providers, toolRegistry, store, options, events, guardrails, prompts, usageTracker, semanticMemory) {
1255
+ this.providers = providers;
1256
+ this.toolRegistry = toolRegistry;
1257
+ this.store = store;
1258
+ this.options = options;
1259
+ this.events = events;
1260
+ this.guardrails = guardrails;
1261
+ this.prompts = prompts;
1262
+ this.usageTracker = usageTracker;
1263
+ this.semanticMemory = semanticMemory;
1264
+ }
1265
+ /** Runs an agent to completion and returns its result. */
1266
+ async run(agent, input, opts = {}) {
1267
+ const meta = this.readMetadata(agent);
1268
+ const agentName = agent.constructor?.name ?? "AiAgent";
1269
+ const model = this.providers.getLanguageModel(opts.model ?? meta.model);
1270
+ const system = await this.resolveSystemWithRecall(opts, meta, input);
1271
+ const schema = opts.schema ?? meta.output;
1272
+ const maxSteps = this.resolveMaxSteps(opts, meta);
1273
+ const newMessages = toMessages(input);
1274
+ const history = await this.loadHistory(opts.conversationId);
1275
+ const ctx = {
1276
+ agent: agentName,
1277
+ messages: [
1278
+ ...history,
1279
+ ...newMessages
1280
+ ],
1281
+ options: opts
1282
+ };
1283
+ this.events?.emit(AI_EVENTS.agentRunStart, {
1284
+ agent: agentName,
1285
+ input,
1286
+ options: opts
1287
+ });
1288
+ try {
1289
+ await this.guardrails?.runBeforeRun(ctx);
1290
+ const result = schema ? await this.runObject(model, system, ctx.messages, schema, opts, newMessages) : await this.runText(model, system, ctx.messages, meta, maxSteps, opts, newMessages);
1291
+ this.usageTracker?.record({
1292
+ model: model.modelId ?? "unknown",
1293
+ usage: result.usage,
1294
+ conversationId: opts.conversationId,
1295
+ agent: agentName
1296
+ });
1297
+ await this.guardrails?.runAfterRun(ctx, result);
1298
+ this.events?.emit(AI_EVENTS.agentRunFinish, {
1299
+ agent: agentName,
1300
+ result
1301
+ });
1302
+ return result;
1303
+ } catch (error) {
1304
+ this.events?.emit(AI_EVENTS.agentRunError, {
1305
+ agent: agentName,
1306
+ error
1307
+ });
1308
+ throw error;
1309
+ }
1310
+ }
1311
+ async runObject(model, system, messages, schema, opts, newMessages) {
1312
+ const result = await generateObject({
1313
+ model,
1314
+ system,
1315
+ messages,
1316
+ schema,
1317
+ abortSignal: opts.abortSignal,
1318
+ temperature: opts.temperature,
1319
+ maxRetries: opts.maxRetries ?? this.options.maxRetries,
1320
+ experimental_telemetry: this.telemetry()
1321
+ });
1322
+ await this.persist(opts.conversationId, newMessages, [
1323
+ {
1324
+ role: "assistant",
1325
+ content: JSON.stringify(result.object)
1326
+ }
1327
+ ]);
1328
+ return {
1329
+ text: "",
1330
+ object: result.object,
1331
+ usage: result.usage,
1332
+ finishReason: result.finishReason,
1333
+ messages: []
1334
+ };
1335
+ }
1336
+ async runText(model, system, messages, meta, maxSteps, opts, newMessages) {
1337
+ const result = await generateText({
1338
+ model,
1339
+ system,
1340
+ messages,
1341
+ tools: this.toolRegistry.buildToolSet(meta.tools),
1342
+ stopWhen: stepCountIs(maxSteps),
1343
+ abortSignal: opts.abortSignal,
1344
+ temperature: opts.temperature,
1345
+ maxRetries: opts.maxRetries ?? this.options.maxRetries,
1346
+ experimental_telemetry: this.telemetry()
1347
+ });
1348
+ await this.persist(opts.conversationId, newMessages, result.response.messages);
1349
+ return {
1350
+ text: result.text,
1351
+ steps: result.steps,
1352
+ toolCalls: result.toolCalls,
1353
+ usage: result.totalUsage,
1354
+ finishReason: result.finishReason,
1355
+ messages: result.response.messages
1356
+ };
1357
+ }
1358
+ /**
1359
+ * Streams an agent's response. Returns the raw Vercel stream result so
1360
+ * controllers can pipe it to an HTTP response or iterate `textStream`.
1361
+ * Conversation persistence happens on stream finish.
1362
+ */
1363
+ stream(agent, input, opts = {}) {
1364
+ const meta = this.readMetadata(agent);
1365
+ const agentName = agent.constructor?.name ?? "AiAgent";
1366
+ const model = this.providers.getLanguageModel(opts.model ?? meta.model);
1367
+ const system = this.resolveSystem(opts, meta);
1368
+ const schema = opts.schema ?? meta.output;
1369
+ const maxSteps = this.resolveMaxSteps(opts, meta);
1370
+ const newMessages = toMessages(input);
1371
+ this.events?.emit(AI_EVENTS.agentRunStart, {
1372
+ agent: agentName,
1373
+ input,
1374
+ options: opts
1375
+ });
1376
+ if (schema) {
1377
+ return streamObject({
1378
+ model,
1379
+ system,
1380
+ messages: newMessages,
1381
+ schema,
1382
+ abortSignal: opts.abortSignal,
1383
+ temperature: opts.temperature,
1384
+ experimental_telemetry: this.telemetry(),
1385
+ onFinish: /* @__PURE__ */ __name(async ({ object }) => {
1386
+ if (object !== void 0) {
1387
+ await this.persist(opts.conversationId, newMessages, [
1388
+ {
1389
+ role: "assistant",
1390
+ content: JSON.stringify(object)
1391
+ }
1392
+ ]);
1393
+ }
1394
+ this.events?.emit(AI_EVENTS.streamFinish, {
1395
+ agent: agentName
1396
+ });
1397
+ }, "onFinish")
1398
+ });
1399
+ }
1400
+ return streamText({
1401
+ model,
1402
+ system,
1403
+ messages: newMessages,
1404
+ tools: this.toolRegistry.buildToolSet(meta.tools),
1405
+ stopWhen: stepCountIs(maxSteps),
1406
+ abortSignal: opts.abortSignal,
1407
+ temperature: opts.temperature,
1408
+ maxRetries: opts.maxRetries ?? this.options.maxRetries,
1409
+ experimental_telemetry: this.telemetry(),
1410
+ onFinish: /* @__PURE__ */ __name(async ({ response }) => {
1411
+ await this.persist(opts.conversationId, newMessages, response.messages);
1412
+ this.events?.emit(AI_EVENTS.streamFinish, {
1413
+ agent: agentName
1414
+ });
1415
+ }, "onFinish")
1416
+ });
1417
+ }
1418
+ /** Resolves the system prompt and prepends recalled memory when requested. */
1419
+ async resolveSystemWithRecall(opts, meta, input) {
1420
+ let system = this.resolveSystem(opts, meta);
1421
+ if (opts.recall && opts.conversationId && this.semanticMemory) {
1422
+ const query = opts.recall.query ?? (typeof input === "string" ? input : "");
1423
+ if (query) {
1424
+ const snippets = await this.semanticMemory.recall(opts.conversationId, query, {
1425
+ topK: opts.recall.topK
1426
+ });
1427
+ if (snippets.length > 0) {
1428
+ const context = snippets.map((s) => s.content).join("\n");
1429
+ system = [
1430
+ system,
1431
+ `Relevant context from memory:
1432
+ ${context}`
1433
+ ].filter(Boolean).join("\n\n");
1434
+ }
1435
+ }
1436
+ }
1437
+ return system;
1438
+ }
1439
+ resolveSystem(opts, meta) {
1440
+ if (opts.systemPrompt) {
1441
+ if (!this.prompts) {
1442
+ throw new Error("systemPrompt requires the PromptRegistry (AiModule must be imported).");
1443
+ }
1444
+ return this.prompts.render(opts.systemPrompt.name, opts.systemPrompt.vars, {
1445
+ version: opts.systemPrompt.version
1446
+ });
1447
+ }
1448
+ return opts.system ?? meta.system;
1449
+ }
1450
+ telemetry() {
1451
+ const t = this.options.telemetry;
1452
+ if (!t?.isEnabled) {
1453
+ return void 0;
1454
+ }
1455
+ return {
1456
+ isEnabled: true,
1457
+ functionId: t.functionId
1458
+ };
1459
+ }
1460
+ readMetadata(agent) {
1461
+ const ctor = agent.constructor;
1462
+ return Reflect.getMetadata(AGENT_METADATA, ctor) ?? {};
1463
+ }
1464
+ resolveMaxSteps(opts, meta) {
1465
+ return opts.maxSteps ?? meta.maxSteps ?? this.options.defaultMaxSteps ?? DEFAULT_MAX_STEPS;
1466
+ }
1467
+ async loadHistory(conversationId) {
1468
+ if (!conversationId) {
1469
+ return [];
1470
+ }
1471
+ return this.store.load(conversationId);
1472
+ }
1473
+ async persist(conversationId, userMessages, responseMessages) {
1474
+ if (!conversationId) {
1475
+ return;
1476
+ }
1477
+ await this.store.append(conversationId, [
1478
+ ...userMessages,
1479
+ ...responseMessages
1480
+ ]);
1481
+ }
1482
+ };
1483
+ AgentExecutorService = _ts_decorate11([
1484
+ Injectable(),
1485
+ _ts_param7(2, Inject(CONVERSATION_STORE)),
1486
+ _ts_param7(3, Inject(AI_MODULE_OPTIONS)),
1487
+ _ts_param7(4, Optional()),
1488
+ _ts_param7(5, Optional()),
1489
+ _ts_param7(6, Optional()),
1490
+ _ts_param7(7, Optional()),
1491
+ _ts_param7(8, Optional()),
1492
+ _ts_metadata10("design:type", Function),
1493
+ _ts_metadata10("design:paramtypes", [
1494
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry,
1495
+ typeof ToolRegistry === "undefined" ? Object : ToolRegistry,
1496
+ typeof ConversationStore === "undefined" ? Object : ConversationStore,
1497
+ typeof AiModuleOptions === "undefined" ? Object : AiModuleOptions,
1498
+ typeof AiEventEmitter === "undefined" ? Object : AiEventEmitter,
1499
+ typeof GuardrailRegistry === "undefined" ? Object : GuardrailRegistry,
1500
+ typeof PromptRegistry === "undefined" ? Object : PromptRegistry,
1501
+ typeof UsageTracker === "undefined" ? Object : UsageTracker,
1502
+ typeof SemanticMemory === "undefined" ? Object : SemanticMemory
1503
+ ])
1504
+ ], AgentExecutorService);
1505
+ function _ts_decorate12(decorators, target, key, desc) {
1506
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1507
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1508
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1509
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1510
+ }
1511
+ __name(_ts_decorate12, "_ts_decorate");
1512
+ var InMemoryConversationStore = class {
1513
+ static {
1514
+ __name(this, "InMemoryConversationStore");
1515
+ }
1516
+ conversations = /* @__PURE__ */ new Map();
1517
+ async load(conversationId) {
1518
+ return [
1519
+ ...this.conversations.get(conversationId) ?? []
1520
+ ];
1521
+ }
1522
+ async append(conversationId, messages) {
1523
+ const existing = this.conversations.get(conversationId) ?? [];
1524
+ this.conversations.set(conversationId, [
1525
+ ...existing,
1526
+ ...messages
1527
+ ]);
1528
+ }
1529
+ async clear(conversationId) {
1530
+ this.conversations.delete(conversationId);
1531
+ }
1532
+ };
1533
+ InMemoryConversationStore = _ts_decorate12([
1534
+ Injectable()
1535
+ ], InMemoryConversationStore);
1536
+ function _ts_decorate13(decorators, target, key, desc) {
1537
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1538
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1539
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1540
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1541
+ }
1542
+ __name(_ts_decorate13, "_ts_decorate");
1543
+ function _ts_metadata11(k, v) {
1544
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1545
+ }
1546
+ __name(_ts_metadata11, "_ts_metadata");
1547
+ var ImageService = class {
1548
+ static {
1549
+ __name(this, "ImageService");
1550
+ }
1551
+ providers;
1552
+ constructor(providers) {
1553
+ this.providers = providers;
1554
+ }
1555
+ generate(prompt, options = {}) {
1556
+ const { model, ...rest } = options;
1557
+ return generateImage({
1558
+ model: this.providers.getImageModel(model),
1559
+ prompt,
1560
+ ...rest
1561
+ });
1562
+ }
1563
+ };
1564
+ ImageService = _ts_decorate13([
1565
+ Injectable(),
1566
+ _ts_metadata11("design:type", Function),
1567
+ _ts_metadata11("design:paramtypes", [
1568
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry
1569
+ ])
1570
+ ], ImageService);
1571
+ function _ts_decorate14(decorators, target, key, desc) {
1572
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1573
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1574
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1575
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1576
+ }
1577
+ __name(_ts_decorate14, "_ts_decorate");
1578
+ function _ts_metadata12(k, v) {
1579
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1580
+ }
1581
+ __name(_ts_metadata12, "_ts_metadata");
1582
+ var SpeechService = class {
1583
+ static {
1584
+ __name(this, "SpeechService");
1585
+ }
1586
+ providers;
1587
+ constructor(providers) {
1588
+ this.providers = providers;
1589
+ }
1590
+ generate(text, options = {}) {
1591
+ const { model, ...rest } = options;
1592
+ return experimental_generateSpeech({
1593
+ model: this.providers.getSpeechModel(model),
1594
+ text,
1595
+ ...rest
1596
+ });
1597
+ }
1598
+ };
1599
+ SpeechService = _ts_decorate14([
1600
+ Injectable(),
1601
+ _ts_metadata12("design:type", Function),
1602
+ _ts_metadata12("design:paramtypes", [
1603
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry
1604
+ ])
1605
+ ], SpeechService);
1606
+ function _ts_decorate15(decorators, target, key, desc) {
1607
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1608
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1609
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1610
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1611
+ }
1612
+ __name(_ts_decorate15, "_ts_decorate");
1613
+ function _ts_metadata13(k, v) {
1614
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1615
+ }
1616
+ __name(_ts_metadata13, "_ts_metadata");
1617
+ var TranscriptionService = class {
1618
+ static {
1619
+ __name(this, "TranscriptionService");
1620
+ }
1621
+ providers;
1622
+ constructor(providers) {
1623
+ this.providers = providers;
1624
+ }
1625
+ transcribe(audio, options = {}) {
1626
+ const { model, ...rest } = options;
1627
+ return experimental_transcribe({
1628
+ model: this.providers.getTranscriptionModel(model),
1629
+ audio,
1630
+ ...rest
1631
+ });
1632
+ }
1633
+ };
1634
+ TranscriptionService = _ts_decorate15([
1635
+ Injectable(),
1636
+ _ts_metadata13("design:type", Function),
1637
+ _ts_metadata13("design:paramtypes", [
1638
+ typeof ProviderRegistry === "undefined" ? Object : ProviderRegistry
1639
+ ])
1640
+ ], TranscriptionService);
1641
+ function _ts_decorate16(decorators, target, key, desc) {
1642
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1643
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1644
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1645
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1646
+ }
1647
+ __name(_ts_decorate16, "_ts_decorate");
1648
+ function _ts_metadata14(k, v) {
1649
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1650
+ }
1651
+ __name(_ts_metadata14, "_ts_metadata");
1652
+ function _ts_param8(paramIndex, decorator) {
1653
+ return function(target, key) {
1654
+ decorator(target, key, paramIndex);
1655
+ };
1656
+ }
1657
+ __name(_ts_param8, "_ts_param");
1658
+ var RagService = class {
1659
+ static {
1660
+ __name(this, "RagService");
1661
+ }
1662
+ embeddings;
1663
+ store;
1664
+ defaultReranker;
1665
+ constructor(embeddings, store, defaultReranker) {
1666
+ this.embeddings = embeddings;
1667
+ this.store = store;
1668
+ this.defaultReranker = defaultReranker;
1669
+ }
1670
+ /** Chunks, embeds, and upserts items into the vector store. */
1671
+ async ingest(items, options = {}) {
1672
+ const chunkSize = options.chunkSize ?? 1e3;
1673
+ const overlap2 = options.chunkOverlap ?? 100;
1674
+ const chunks = [];
1675
+ items.forEach((item, index) => {
1676
+ const baseId = item.id ?? `doc-${index}`;
1677
+ splitText(item.content, chunkSize, overlap2).forEach((text, chunkIndex) => {
1678
+ chunks.push({
1679
+ id: `${baseId}#${chunkIndex}`,
1680
+ content: text,
1681
+ metadata: item.metadata
1682
+ });
1683
+ });
1684
+ });
1685
+ if (chunks.length === 0) {
1686
+ return;
1687
+ }
1688
+ const { embeddings } = await this.embeddings.embedMany(chunks.map((c) => c.content), {
1689
+ model: options.model
1690
+ });
1691
+ const documents = chunks.map((chunk, i) => ({
1692
+ ...chunk,
1693
+ embedding: embeddings[i]
1694
+ }));
1695
+ await this.store.upsert(documents);
1696
+ }
1697
+ /** Embeds `query` and returns the most similar stored chunks. */
1698
+ async retrieve(query, options = {}) {
1699
+ const { embedding } = await this.embeddings.embed(query, {
1700
+ model: options.model
1701
+ });
1702
+ const topK = options.topK ?? 4;
1703
+ const reranker = options.rerank === true ? this.defaultReranker : options.rerank || void 0;
1704
+ const fetchK = reranker ? options.fetchK ?? topK * 4 : topK;
1705
+ const results = await this.store.query(embedding, {
1706
+ topK: fetchK,
1707
+ filter: options.filter
1708
+ });
1709
+ if (reranker) {
1710
+ return reranker.rerank(query, results, topK);
1711
+ }
1712
+ return results.slice(0, topK);
1713
+ }
1714
+ };
1715
+ RagService = _ts_decorate16([
1716
+ Injectable(),
1717
+ _ts_param8(1, Inject(VECTOR_STORE)),
1718
+ _ts_param8(2, Optional()),
1719
+ _ts_param8(2, Inject(RERANKER)),
1720
+ _ts_metadata14("design:type", Function),
1721
+ _ts_metadata14("design:paramtypes", [
1722
+ typeof EmbeddingsService === "undefined" ? Object : EmbeddingsService,
1723
+ typeof VectorStore === "undefined" ? Object : VectorStore,
1724
+ typeof Reranker === "undefined" ? Object : Reranker
1725
+ ])
1726
+ ], RagService);
1727
+ function splitText(text, chunkSize, overlap2) {
1728
+ if (chunkSize <= 0 || text.length <= chunkSize) {
1729
+ return text.length > 0 ? [
1730
+ text
1731
+ ] : [];
1732
+ }
1733
+ const step = Math.max(1, chunkSize - overlap2);
1734
+ const chunks = [];
1735
+ for (let start = 0; start < text.length; start += step) {
1736
+ chunks.push(text.slice(start, start + chunkSize));
1737
+ if (start + chunkSize >= text.length) {
1738
+ break;
1739
+ }
1740
+ }
1741
+ return chunks;
1742
+ }
1743
+ __name(splitText, "splitText");
1744
+ function _ts_decorate17(decorators, target, key, desc) {
1745
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1746
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1747
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1748
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1749
+ }
1750
+ __name(_ts_decorate17, "_ts_decorate");
1751
+ var InMemoryVectorStore = class {
1752
+ static {
1753
+ __name(this, "InMemoryVectorStore");
1754
+ }
1755
+ documents = /* @__PURE__ */ new Map();
1756
+ async upsert(documents) {
1757
+ for (const doc of documents) {
1758
+ if (!doc.embedding) {
1759
+ throw new Error(`Document "${doc.id}" has no embedding. InMemoryVectorStore requires precomputed embeddings (use RagService.ingest).`);
1760
+ }
1761
+ this.documents.set(doc.id, doc);
1762
+ }
1763
+ }
1764
+ async query(embedding, options = {}) {
1765
+ const topK = options.topK ?? 4;
1766
+ const filter = options.filter;
1767
+ const scored = [];
1768
+ for (const doc of this.documents.values()) {
1769
+ if (filter && !this.matchesFilter(doc, filter)) {
1770
+ continue;
1771
+ }
1772
+ scored.push({
1773
+ id: doc.id,
1774
+ content: doc.content,
1775
+ score: cosineSimilarity(embedding, doc.embedding),
1776
+ metadata: doc.metadata
1777
+ });
1778
+ }
1779
+ return scored.sort((a, b) => b.score - a.score).slice(0, topK);
1780
+ }
1781
+ async delete(ids) {
1782
+ for (const id of ids) {
1783
+ this.documents.delete(id);
1784
+ }
1785
+ }
1786
+ async clear() {
1787
+ this.documents.clear();
1788
+ }
1789
+ matchesFilter(doc, filter) {
1790
+ return Object.entries(filter).every(([key, value]) => doc.metadata?.[key] === value);
1791
+ }
1792
+ };
1793
+ InMemoryVectorStore = _ts_decorate17([
1794
+ Injectable()
1795
+ ], InMemoryVectorStore);
1796
+ function _ts_decorate18(decorators, target, key, desc) {
1797
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1798
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1799
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1800
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1801
+ }
1802
+ __name(_ts_decorate18, "_ts_decorate");
1803
+ var McpService = class {
1804
+ static {
1805
+ __name(this, "McpService");
1806
+ }
1807
+ clients = /* @__PURE__ */ new Map();
1808
+ toolSets = /* @__PURE__ */ new Map();
1809
+ /**
1810
+ * Registers an MCP client under `name`, lists its tools, and builds a
1811
+ * matching AI SDK tool set. Returns the tool set.
1812
+ */
1813
+ async connect(name, client) {
1814
+ const { tools } = await client.listTools();
1815
+ const set = {};
1816
+ for (const info of tools) {
1817
+ set[info.name] = dynamicTool({
1818
+ description: info.description ?? info.name,
1819
+ inputSchema: jsonSchema(info.inputSchema),
1820
+ execute: /* @__PURE__ */ __name(async (args) => {
1821
+ const result = await client.callTool({
1822
+ name: info.name,
1823
+ arguments: args ?? {}
1824
+ });
1825
+ return extractText(result);
1826
+ }, "execute")
1827
+ });
1828
+ }
1829
+ this.clients.set(name, client);
1830
+ this.toolSets.set(name, set);
1831
+ return set;
1832
+ }
1833
+ /** Returns the tool set for a connected server (empty if unknown). */
1834
+ getToolSet(name) {
1835
+ return this.toolSets.get(name) ?? {};
1836
+ }
1837
+ /** Returns tool sets for all connected servers, merged. */
1838
+ getAllTools() {
1839
+ return Object.assign({}, ...this.toolSets.values());
1840
+ }
1841
+ async onModuleDestroy() {
1842
+ await this.closeAll();
1843
+ }
1844
+ /** Closes every connected client. */
1845
+ async closeAll() {
1846
+ for (const client of this.clients.values()) {
1847
+ await client.close?.();
1848
+ }
1849
+ this.clients.clear();
1850
+ this.toolSets.clear();
1851
+ }
1852
+ };
1853
+ McpService = _ts_decorate18([
1854
+ Injectable()
1855
+ ], McpService);
1856
+ function extractText(result) {
1857
+ if (!result.content) {
1858
+ return "";
1859
+ }
1860
+ return result.content.filter((part) => part.type === "text" && typeof part.text === "string").map((part) => part.text).join("\n");
1861
+ }
1862
+ __name(extractText, "extractText");
1863
+ function Guardrail() {
1864
+ return (target) => {
1865
+ Reflect.defineMetadata(GUARDRAIL_METADATA, true, target);
1866
+ Injectable()(target);
1867
+ };
1868
+ }
1869
+ __name(Guardrail, "Guardrail");
1870
+
1871
+ // src/usage/budget.guardrail.ts
1872
+ function _ts_decorate19(decorators, target, key, desc) {
1873
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1874
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1875
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1876
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1877
+ }
1878
+ __name(_ts_decorate19, "_ts_decorate");
1879
+ function _ts_metadata15(k, v) {
1880
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1881
+ }
1882
+ __name(_ts_metadata15, "_ts_metadata");
1883
+ function _ts_param9(paramIndex, decorator) {
1884
+ return function(target, key) {
1885
+ decorator(target, key, paramIndex);
1886
+ };
1887
+ }
1888
+ __name(_ts_param9, "_ts_param");
1889
+ var BudgetExceededError = class extends Error {
1890
+ static {
1891
+ __name(this, "BudgetExceededError");
1892
+ }
1893
+ conversationId;
1894
+ spent;
1895
+ limit;
1896
+ constructor(conversationId, spent, limit) {
1897
+ super(`Budget exceeded${conversationId ? ` for "${conversationId}"` : ""}: $${spent.toFixed(4)} >= $${limit.toFixed(4)}.`), this.conversationId = conversationId, this.spent = spent, this.limit = limit;
1898
+ this.name = "BudgetExceededError";
1899
+ }
1900
+ };
1901
+ var BudgetGuard = class {
1902
+ static {
1903
+ __name(this, "BudgetGuard");
1904
+ }
1905
+ usage;
1906
+ options;
1907
+ constructor(usage, options) {
1908
+ this.usage = usage;
1909
+ this.options = options;
1910
+ }
1911
+ beforeRun(ctx) {
1912
+ const limit = this.options.maxCostPerConversation;
1913
+ if (limit == null) {
1914
+ return;
1915
+ }
1916
+ const { cost } = this.usage.totals(ctx.options.conversationId);
1917
+ if (cost >= limit) {
1918
+ throw new BudgetExceededError(ctx.options.conversationId, cost, limit);
1919
+ }
1920
+ }
1921
+ };
1922
+ BudgetGuard = _ts_decorate19([
1923
+ Guardrail(),
1924
+ Injectable(),
1925
+ _ts_param9(1, Inject(AI_MODULE_OPTIONS)),
1926
+ _ts_metadata15("design:type", Function),
1927
+ _ts_metadata15("design:paramtypes", [
1928
+ typeof UsageTracker === "undefined" ? Object : UsageTracker,
1929
+ typeof AiModuleOptions === "undefined" ? Object : AiModuleOptions
1930
+ ])
1931
+ ], BudgetGuard);
1932
+
1933
+ // src/ratelimit/rate-limiter.interface.ts
1934
+ var RateLimitedError = class extends Error {
1935
+ static {
1936
+ __name(this, "RateLimitedError");
1937
+ }
1938
+ key;
1939
+ constructor(key) {
1940
+ super(`Rate limit exceeded for "${key}".`), this.key = key;
1941
+ this.name = "RateLimitedError";
1942
+ }
1943
+ };
1944
+
1945
+ // src/ratelimit/rate-limit.guardrail.ts
1946
+ function _ts_decorate20(decorators, target, key, desc) {
1947
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1948
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1949
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1950
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1951
+ }
1952
+ __name(_ts_decorate20, "_ts_decorate");
1953
+ function _ts_metadata16(k, v) {
1954
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1955
+ }
1956
+ __name(_ts_metadata16, "_ts_metadata");
1957
+ function _ts_param10(paramIndex, decorator) {
1958
+ return function(target, key) {
1959
+ decorator(target, key, paramIndex);
1960
+ };
1961
+ }
1962
+ __name(_ts_param10, "_ts_param");
1963
+ var RateLimitGuardrail = class {
1964
+ static {
1965
+ __name(this, "RateLimitGuardrail");
1966
+ }
1967
+ limiter;
1968
+ constructor(limiter) {
1969
+ this.limiter = limiter;
1970
+ }
1971
+ async beforeRun(ctx) {
1972
+ const key = ctx.options.conversationId ?? "global";
1973
+ const allowed = await this.limiter.consume(key);
1974
+ if (!allowed) {
1975
+ throw new RateLimitedError(key);
1976
+ }
1977
+ }
1978
+ };
1979
+ RateLimitGuardrail = _ts_decorate20([
1980
+ Guardrail(),
1981
+ Injectable(),
1982
+ _ts_param10(0, Inject(RATE_LIMITER)),
1983
+ _ts_metadata16("design:type", Function),
1984
+ _ts_metadata16("design:paramtypes", [
1985
+ typeof RateLimiter === "undefined" ? Object : RateLimiter
1986
+ ])
1987
+ ], RateLimitGuardrail);
1988
+ function _ts_decorate21(decorators, target, key, desc) {
1989
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
1990
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
1991
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
1992
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
1993
+ }
1994
+ __name(_ts_decorate21, "_ts_decorate");
1995
+ function _ts_metadata17(k, v) {
1996
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
1997
+ }
1998
+ __name(_ts_metadata17, "_ts_metadata");
1999
+ function _ts_param11(paramIndex, decorator) {
2000
+ return function(target, key) {
2001
+ decorator(target, key, paramIndex);
2002
+ };
2003
+ }
2004
+ __name(_ts_param11, "_ts_param");
2005
+ var HeuristicReranker = class {
2006
+ static {
2007
+ __name(this, "HeuristicReranker");
2008
+ }
2009
+ options;
2010
+ constructor(options = {}) {
2011
+ this.options = options;
2012
+ }
2013
+ async rerank(query, results, topN) {
2014
+ const weight = this.options.overlapWeight ?? 0.5;
2015
+ const terms = tokenize(query);
2016
+ return results.map((result) => ({
2017
+ result,
2018
+ score: result.score + weight * overlap(terms, result.content)
2019
+ })).sort((a, b) => b.score - a.score).slice(0, topN).map(({ result, score }) => ({
2020
+ ...result,
2021
+ score
2022
+ }));
2023
+ }
2024
+ };
2025
+ HeuristicReranker = _ts_decorate21([
2026
+ Injectable(),
2027
+ _ts_param11(0, Optional()),
2028
+ _ts_metadata17("design:type", Function),
2029
+ _ts_metadata17("design:paramtypes", [
2030
+ typeof HeuristicRerankerOptions === "undefined" ? Object : HeuristicRerankerOptions
2031
+ ])
2032
+ ], HeuristicReranker);
2033
+ function tokenize(text) {
2034
+ return new Set(text.toLowerCase().split(/[^a-z0-9]+/).filter((t) => t.length > 2));
2035
+ }
2036
+ __name(tokenize, "tokenize");
2037
+ function overlap(terms, content) {
2038
+ if (terms.size === 0) {
2039
+ return 0;
2040
+ }
2041
+ const contentTerms = tokenize(content);
2042
+ let hits = 0;
2043
+ for (const term of terms) {
2044
+ if (contentTerms.has(term)) {
2045
+ hits++;
2046
+ }
2047
+ }
2048
+ return hits / terms.size;
2049
+ }
2050
+ __name(overlap, "overlap");
2051
+ function _ts_decorate22(decorators, target, key, desc) {
2052
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
2053
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
2054
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
2055
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
2056
+ }
2057
+ __name(_ts_decorate22, "_ts_decorate");
2058
+ var EvalRunner = class {
2059
+ static {
2060
+ __name(this, "EvalRunner");
2061
+ }
2062
+ async run(agent, cases, options = {}) {
2063
+ const judge = options.judge ?? defaultJudge(options.passThreshold ?? 1);
2064
+ const results = [];
2065
+ for (const evalCase of cases) {
2066
+ const { text } = await agent.run(evalCase.input);
2067
+ const score = await judge({
2068
+ case: evalCase,
2069
+ output: text
2070
+ });
2071
+ results.push({
2072
+ name: evalCase.name ?? evalCase.input,
2073
+ input: evalCase.input,
2074
+ output: text,
2075
+ ...score
2076
+ });
2077
+ }
2078
+ const averageScore = results.length ? results.reduce((sum, r) => sum + r.score, 0) / results.length : 0;
2079
+ const passRate = results.length ? results.filter((r) => r.passed).length / results.length : 0;
2080
+ return {
2081
+ results,
2082
+ averageScore,
2083
+ passRate
2084
+ };
2085
+ }
2086
+ };
2087
+ EvalRunner = _ts_decorate22([
2088
+ Injectable()
2089
+ ], EvalRunner);
2090
+ function defaultJudge(threshold) {
2091
+ return ({ case: evalCase, output }) => {
2092
+ if (evalCase.expected == null) {
2093
+ return {
2094
+ score: 0,
2095
+ passed: false,
2096
+ reasoning: "no expected value or judge"
2097
+ };
2098
+ }
2099
+ const score = output.includes(evalCase.expected) ? 1 : 0;
2100
+ return {
2101
+ score,
2102
+ passed: score >= threshold
2103
+ };
2104
+ };
2105
+ }
2106
+ __name(defaultJudge, "defaultJudge");
2107
+
2108
+ // src/ai.module.ts
2109
+ function _ts_decorate23(decorators, target, key, desc) {
2110
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
2111
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
2112
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
2113
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
2114
+ }
2115
+ __name(_ts_decorate23, "_ts_decorate");
2116
+ var AI_INITIALIZER = /* @__PURE__ */ Symbol("AI_INITIALIZER");
2117
+ var AiModule = class _AiModule {
2118
+ static {
2119
+ __name(this, "AiModule");
2120
+ }
2121
+ /** Configure the module with static options. */
2122
+ static forRoot(options = {}) {
2123
+ return _AiModule.build({
2124
+ provide: AI_MODULE_OPTIONS,
2125
+ useValue: options
2126
+ }, options);
2127
+ }
2128
+ /** Configure the module asynchronously (e.g. from `ConfigService`). */
2129
+ static forRootAsync(options) {
2130
+ return _AiModule.build({
2131
+ provide: AI_MODULE_OPTIONS,
2132
+ useFactory: options.useFactory,
2133
+ inject: options.inject ?? []
2134
+ }, options, options.imports);
2135
+ }
2136
+ /**
2137
+ * Convenience registration of agents / tools / guardrails so they don't have
2138
+ * to be added to a consuming module's own `providers` array, plus feature
2139
+ * prompts. Discovery still finds providers globally regardless of where they
2140
+ * are registered.
2141
+ */
2142
+ static forFeature(feature = {}) {
2143
+ const providers = [
2144
+ ...feature.agents ?? [],
2145
+ ...feature.tools ?? [],
2146
+ ...feature.guardrails ?? []
2147
+ ];
2148
+ if (feature.prompts?.length) {
2149
+ providers.push({
2150
+ provide: /* @__PURE__ */ Symbol("AI_FEATURE_PROMPTS"),
2151
+ useFactory: /* @__PURE__ */ __name((registry) => {
2152
+ registry.registerAll(feature.prompts);
2153
+ return true;
2154
+ }, "useFactory"),
2155
+ inject: [
2156
+ PromptRegistry
2157
+ ]
2158
+ });
2159
+ }
2160
+ return {
2161
+ module: _AiModule,
2162
+ providers,
2163
+ exports: providers
2164
+ };
2165
+ }
2166
+ static build(optionsProvider, options, extraImports = []) {
2167
+ return {
2168
+ module: _AiModule,
2169
+ imports: [
2170
+ DiscoveryModule,
2171
+ ...extraImports ?? []
2172
+ ],
2173
+ providers: [
2174
+ optionsProvider,
2175
+ _AiModule.storeProvider(options.conversationStore),
2176
+ _AiModule.vectorStoreProvider(options.vectorStore),
2177
+ _AiModule.eventEmitterProvider(),
2178
+ ..._AiModule.tokenProvider(AI_CACHE, options.cache),
2179
+ ..._AiModule.tokenProvider(APPROVAL_GATE, options.approvalGate),
2180
+ ..._AiModule.tokenProvider(RATE_LIMITER, options.rateLimiter),
2181
+ ..._AiModule.guardrailClasses(options.guardrails),
2182
+ ...options.maxCostPerConversation != null ? [
2183
+ BudgetGuard
2184
+ ] : [],
2185
+ ...options.rateLimiter ? [
2186
+ RateLimitGuardrail
2187
+ ] : [],
2188
+ ..._AiModule.coreProviders(),
2189
+ _AiModule.initializerProvider()
2190
+ ],
2191
+ exports: _AiModule.exportedTokens()
2192
+ };
2193
+ }
2194
+ static coreProviders() {
2195
+ return [
2196
+ ProviderRegistry,
2197
+ ToolRegistry,
2198
+ AgentExecutorService,
2199
+ AgentRegistry,
2200
+ AiService,
2201
+ EmbeddingsService,
2202
+ ImageService,
2203
+ SpeechService,
2204
+ TranscriptionService,
2205
+ RagService,
2206
+ PromptRegistry,
2207
+ AiEventEmitter,
2208
+ GuardrailRegistry,
2209
+ McpService,
2210
+ UsageTracker,
2211
+ SemanticMemory,
2212
+ EvalRunner,
2213
+ {
2214
+ provide: RERANKER,
2215
+ useFactory: /* @__PURE__ */ __name(() => new HeuristicReranker(), "useFactory")
2216
+ }
2217
+ ];
2218
+ }
2219
+ /**
2220
+ * Registers an optional provider (class / factory / value / useClass shape)
2221
+ * under `token`, or nothing when not configured.
2222
+ */
2223
+ static tokenProvider(token, config) {
2224
+ if (!config) {
2225
+ return [];
2226
+ }
2227
+ if (typeof config === "function") {
2228
+ return [
2229
+ {
2230
+ provide: token,
2231
+ useClass: config
2232
+ }
2233
+ ];
2234
+ }
2235
+ return [
2236
+ {
2237
+ provide: token,
2238
+ ...config
2239
+ }
2240
+ ];
2241
+ }
2242
+ static exportedTokens() {
2243
+ return [
2244
+ ProviderRegistry,
2245
+ ToolRegistry,
2246
+ AgentExecutorService,
2247
+ AgentRegistry,
2248
+ AiService,
2249
+ EmbeddingsService,
2250
+ ImageService,
2251
+ SpeechService,
2252
+ TranscriptionService,
2253
+ RagService,
2254
+ PromptRegistry,
2255
+ AiEventEmitter,
2256
+ GuardrailRegistry,
2257
+ McpService,
2258
+ UsageTracker,
2259
+ SemanticMemory,
2260
+ EvalRunner,
2261
+ RERANKER,
2262
+ CONVERSATION_STORE,
2263
+ VECTOR_STORE,
2264
+ AI_MODULE_OPTIONS
2265
+ ];
2266
+ }
2267
+ static guardrailClasses(guardrails) {
2268
+ return guardrails ?? [];
2269
+ }
2270
+ /** Seeds prompts (and future startup wiring) once dependencies exist. */
2271
+ static initializerProvider() {
2272
+ return {
2273
+ provide: AI_INITIALIZER,
2274
+ useFactory: /* @__PURE__ */ __name((registry, opts) => {
2275
+ if (opts.prompts?.length) {
2276
+ registry.registerAll(opts.prompts);
2277
+ }
2278
+ return true;
2279
+ }, "useFactory"),
2280
+ inject: [
2281
+ PromptRegistry,
2282
+ AI_MODULE_OPTIONS
2283
+ ]
2284
+ };
2285
+ }
2286
+ /**
2287
+ * Optionally resolves `EventEmitter2` from `@nestjs/event-emitter` if the
2288
+ * package is installed and its module is imported; otherwise `undefined`.
2289
+ */
2290
+ static eventEmitterProvider() {
2291
+ return {
2292
+ provide: EVENT_EMITTER,
2293
+ useFactory: /* @__PURE__ */ __name(async (moduleRef) => {
2294
+ try {
2295
+ const mod = await import('@nestjs/event-emitter');
2296
+ return moduleRef.get(mod.EventEmitter2, {
2297
+ strict: false
2298
+ });
2299
+ } catch {
2300
+ return void 0;
2301
+ }
2302
+ }, "useFactory"),
2303
+ inject: [
2304
+ ModuleRef
2305
+ ]
2306
+ };
2307
+ }
2308
+ static storeProvider(store) {
2309
+ if (!store) {
2310
+ return {
2311
+ provide: CONVERSATION_STORE,
2312
+ useClass: InMemoryConversationStore
2313
+ };
2314
+ }
2315
+ if (typeof store === "function") {
2316
+ return {
2317
+ provide: CONVERSATION_STORE,
2318
+ useClass: store
2319
+ };
2320
+ }
2321
+ return {
2322
+ provide: CONVERSATION_STORE,
2323
+ ...store
2324
+ };
2325
+ }
2326
+ static vectorStoreProvider(store) {
2327
+ if (!store) {
2328
+ return {
2329
+ provide: VECTOR_STORE,
2330
+ useClass: InMemoryVectorStore
2331
+ };
2332
+ }
2333
+ if (typeof store === "function") {
2334
+ return {
2335
+ provide: VECTOR_STORE,
2336
+ useClass: store
2337
+ };
2338
+ }
2339
+ return {
2340
+ provide: VECTOR_STORE,
2341
+ ...store
2342
+ };
2343
+ }
2344
+ };
2345
+ AiModule = _ts_decorate23([
2346
+ Global(),
2347
+ Module({})
2348
+ ], AiModule);
2349
+
2350
+ // src/testing/testing.module.ts
2351
+ async function createTestingAiModule(options = {}) {
2352
+ const model = options.model ?? createMockModel("mock response");
2353
+ const embedding = options.embedding ?? createEmbeddingMock(() => [
2354
+ 0
2355
+ ]);
2356
+ const moduleRef = await Test.createTestingModule({
2357
+ imports: [
2358
+ AiModule.forRoot(options.aiOptions ?? {
2359
+ providers: {
2360
+ openai: {
2361
+ apiKey: "test"
2362
+ }
2363
+ }
2364
+ }),
2365
+ ...options.imports ?? []
2366
+ ],
2367
+ providers: options.providers ?? []
2368
+ }).overrideProvider(ProviderRegistry).useValue({
2369
+ getLanguageModel: /* @__PURE__ */ __name(() => model, "getLanguageModel"),
2370
+ getEmbeddingModel: /* @__PURE__ */ __name(() => embedding, "getEmbeddingModel"),
2371
+ getImageModel: /* @__PURE__ */ __name(() => {
2372
+ throw new Error("No image model mock configured.");
2373
+ }, "getImageModel"),
2374
+ getSpeechModel: /* @__PURE__ */ __name(() => {
2375
+ throw new Error("No speech model mock configured.");
2376
+ }, "getSpeechModel"),
2377
+ getTranscriptionModel: /* @__PURE__ */ __name(() => {
2378
+ throw new Error("No transcription model mock configured.");
2379
+ }, "getTranscriptionModel"),
2380
+ getRerankingModel: /* @__PURE__ */ __name(() => {
2381
+ throw new Error("No reranking model mock configured.");
2382
+ }, "getRerankingModel")
2383
+ }).compile();
2384
+ await moduleRef.init();
2385
+ return moduleRef;
2386
+ }
2387
+ __name(createTestingAiModule, "createTestingAiModule");
2388
+
2389
+ export { createEmbeddingMock, createMockModel, createTestingAiModule };
2390
+ //# sourceMappingURL=testing.js.map
2391
+ //# sourceMappingURL=testing.js.map