@objectstack/service-ai 4.0.0 → 4.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build.log +11 -11
- package/CHANGELOG.md +20 -0
- package/dist/index.cjs +1245 -54
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +344 -77
- package/dist/index.d.ts +344 -77
- package/dist/index.js +1230 -51
- package/dist/index.js.map +1 -1
- package/package.json +26 -4
- package/src/__tests__/ai-service.test.ts +248 -27
- package/src/__tests__/auth-and-toolcalling.test.ts +627 -0
- package/src/__tests__/chatbot-features.test.ts +229 -82
- package/src/__tests__/metadata-tools.test.ts +964 -0
- package/src/__tests__/objectql-conversation-service.test.ts +34 -16
- package/src/__tests__/vercel-stream-encoder.test.ts +263 -0
- package/src/adapters/index.ts +2 -0
- package/src/adapters/memory-adapter.ts +17 -9
- package/src/adapters/vercel-adapter.ts +148 -0
- package/src/agent-runtime.ts +27 -3
- package/src/agents/index.ts +1 -0
- package/src/agents/metadata-assistant-agent.ts +87 -0
- package/src/ai-service.ts +174 -22
- package/src/conversation/in-memory-conversation-service.ts +2 -2
- package/src/conversation/objectql-conversation-service.ts +67 -18
- package/src/index.ts +22 -3
- package/src/plugin.ts +166 -9
- package/src/routes/agent-routes.ts +28 -3
- package/src/routes/ai-routes.ts +231 -14
- package/src/routes/index.ts +1 -1
- package/src/stream/index.ts +3 -0
- package/src/stream/vercel-stream-encoder.ts +129 -0
- package/src/tools/add-field.tool.ts +70 -0
- package/src/tools/create-object.tool.ts +66 -0
- package/src/tools/delete-field.tool.ts +38 -0
- package/src/tools/describe-metadata-object.tool.ts +32 -0
- package/src/tools/index.ts +12 -1
- package/src/tools/list-metadata-objects.tool.ts +34 -0
- package/src/tools/metadata-tools.ts +430 -0
- package/src/tools/modify-field.tool.ts +44 -0
- package/src/tools/tool-registry.ts +32 -9
package/dist/index.d.cts
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
|
-
import { AIToolDefinition,
|
|
1
|
+
import { AIToolDefinition, ToolCallPart, ToolResultPart, IAIService, IAIConversationService, LLMAdapter, Logger, ModelMessage, AIRequestOptions, AIResult, TextStreamPart, ToolSet, ChatWithToolsOptions, AIConversation, IDataEngine, IMetadataService } from '@objectstack/spec/contracts';
|
|
2
2
|
export { LLMAdapter } from '@objectstack/spec/contracts';
|
|
3
3
|
import { Plugin, PluginContext } from '@objectstack/core';
|
|
4
|
+
import { LanguageModelV2 } from '@ai-sdk/provider';
|
|
5
|
+
import { TextStreamPart as TextStreamPart$1, ToolSet as ToolSet$1 } from 'ai';
|
|
6
|
+
import { Tool } from '@objectstack/spec/ai';
|
|
4
7
|
import { Agent } from '@objectstack/spec';
|
|
5
8
|
import { z } from 'zod';
|
|
6
9
|
import * as _objectstack_spec_data from '@objectstack/spec/data';
|
|
@@ -11,6 +14,13 @@ import * as _objectstack_spec_data from '@objectstack/spec/data';
|
|
|
11
14
|
* Receives parsed arguments and returns the tool output as a string.
|
|
12
15
|
*/
|
|
13
16
|
type ToolHandler = (args: Record<string, unknown>) => Promise<string> | string;
|
|
17
|
+
/**
|
|
18
|
+
* Extended ToolResultPart that carries an `isError` flag for internal
|
|
19
|
+
* error-tracking in the tool-call loop.
|
|
20
|
+
*/
|
|
21
|
+
interface ToolExecutionResult extends ToolResultPart {
|
|
22
|
+
isError?: boolean;
|
|
23
|
+
}
|
|
14
24
|
/**
|
|
15
25
|
* ToolRegistry — Central registry for AI-callable tools.
|
|
16
26
|
*
|
|
@@ -50,11 +60,11 @@ declare class ToolRegistry {
|
|
|
50
60
|
/**
|
|
51
61
|
* Execute a tool call and return the result.
|
|
52
62
|
*/
|
|
53
|
-
execute(toolCall:
|
|
63
|
+
execute(toolCall: ToolCallPart): Promise<ToolExecutionResult>;
|
|
54
64
|
/**
|
|
55
65
|
* Execute multiple tool calls in parallel.
|
|
56
66
|
*/
|
|
57
|
-
executeAll(toolCalls:
|
|
67
|
+
executeAll(toolCalls: ToolCallPart[]): Promise<ToolExecutionResult[]>;
|
|
58
68
|
/**
|
|
59
69
|
* Clear all registered tools.
|
|
60
70
|
*/
|
|
@@ -97,13 +107,15 @@ declare class AIService implements IAIService {
|
|
|
97
107
|
constructor(config?: AIServiceConfig);
|
|
98
108
|
/** The name of the active LLM adapter. */
|
|
99
109
|
get adapterName(): string;
|
|
100
|
-
chat(messages:
|
|
110
|
+
chat(messages: ModelMessage[], options?: AIRequestOptions): Promise<AIResult>;
|
|
101
111
|
complete(prompt: string, options?: AIRequestOptions): Promise<AIResult>;
|
|
102
|
-
streamChat(messages:
|
|
112
|
+
streamChat(messages: ModelMessage[], options?: AIRequestOptions): AsyncIterable<TextStreamPart<ToolSet>>;
|
|
103
113
|
embed(input: string | string[], model?: string): Promise<number[][]>;
|
|
104
114
|
listModels(): Promise<string[]>;
|
|
105
115
|
/** Default maximum iterations for the tool call loop. */
|
|
106
116
|
static readonly DEFAULT_MAX_ITERATIONS = 10;
|
|
117
|
+
/** Extract the text value from a ToolExecutionResult's output. */
|
|
118
|
+
private static extractOutputText;
|
|
107
119
|
/**
|
|
108
120
|
* Chat with automatic tool call resolution.
|
|
109
121
|
*
|
|
@@ -115,7 +127,15 @@ declare class AIService implements IAIService {
|
|
|
115
127
|
* 4. Repeats until the model produces a final text response or the
|
|
116
128
|
* maximum number of iterations (`maxIterations`) is reached.
|
|
117
129
|
*/
|
|
118
|
-
chatWithTools(messages:
|
|
130
|
+
chatWithTools(messages: ModelMessage[], options?: ChatWithToolsOptions): Promise<AIResult>;
|
|
131
|
+
/**
|
|
132
|
+
* Stream chat with automatic tool call resolution.
|
|
133
|
+
*
|
|
134
|
+
* Works like {@link chatWithTools} but yields SSE events. When the model
|
|
135
|
+
* requests tool calls during streaming, they are executed and the results
|
|
136
|
+
* fed back until a final text stream is produced.
|
|
137
|
+
*/
|
|
138
|
+
streamChatWithTools(messages: ModelMessage[], options?: ChatWithToolsOptions): AsyncIterable<TextStreamPart<ToolSet>>;
|
|
119
139
|
}
|
|
120
140
|
|
|
121
141
|
/**
|
|
@@ -160,6 +180,19 @@ declare class AIServicePlugin implements Plugin {
|
|
|
160
180
|
private service?;
|
|
161
181
|
private readonly options;
|
|
162
182
|
constructor(options?: AIServicePluginOptions);
|
|
183
|
+
/**
|
|
184
|
+
* Auto-detect LLM provider from environment variables.
|
|
185
|
+
*
|
|
186
|
+
* Priority order:
|
|
187
|
+
* 1. AI_GATEWAY_MODEL → Vercel AI Gateway
|
|
188
|
+
* 2. OPENAI_API_KEY → OpenAI
|
|
189
|
+
* 3. ANTHROPIC_API_KEY → Anthropic
|
|
190
|
+
* 4. GOOGLE_GENERATIVE_AI_API_KEY → Google
|
|
191
|
+
* 5. Fallback → MemoryLLMAdapter
|
|
192
|
+
*
|
|
193
|
+
* Returns the adapter and a description for logging.
|
|
194
|
+
*/
|
|
195
|
+
private detectAdapter;
|
|
163
196
|
init(ctx: PluginContext): Promise<void>;
|
|
164
197
|
start(ctx: PluginContext): Promise<void>;
|
|
165
198
|
destroy(): Promise<void>;
|
|
@@ -173,13 +206,81 @@ declare class AIServicePlugin implements Plugin {
|
|
|
173
206
|
*/
|
|
174
207
|
declare class MemoryLLMAdapter implements LLMAdapter {
|
|
175
208
|
readonly name = "memory";
|
|
176
|
-
chat(messages:
|
|
209
|
+
chat(messages: ModelMessage[], options?: AIRequestOptions): Promise<AIResult>;
|
|
177
210
|
complete(prompt: string, options?: AIRequestOptions): Promise<AIResult>;
|
|
178
|
-
streamChat(messages:
|
|
211
|
+
streamChat(messages: ModelMessage[], _options?: AIRequestOptions): AsyncIterable<TextStreamPart<ToolSet>>;
|
|
179
212
|
embed(input: string | string[]): Promise<number[][]>;
|
|
180
213
|
listModels(): Promise<string[]>;
|
|
181
214
|
}
|
|
182
215
|
|
|
216
|
+
/**
|
|
217
|
+
* VercelLLMAdapter — Production LLM adapter powered by the Vercel AI SDK.
|
|
218
|
+
*
|
|
219
|
+
* Wraps `generateText` / `streamText` from the `ai` package, delegating to
|
|
220
|
+
* any Vercel AI SDK–compatible model provider (OpenAI, Anthropic, Google,
|
|
221
|
+
* Ollama, etc.).
|
|
222
|
+
*
|
|
223
|
+
* @example
|
|
224
|
+
* ```typescript
|
|
225
|
+
* import { openai } from '@ai-sdk/openai';
|
|
226
|
+
* import { VercelLLMAdapter } from '@objectstack/service-ai';
|
|
227
|
+
*
|
|
228
|
+
* const adapter = new VercelLLMAdapter({ model: openai('gpt-4o') });
|
|
229
|
+
* ```
|
|
230
|
+
*/
|
|
231
|
+
declare class VercelLLMAdapter implements LLMAdapter {
|
|
232
|
+
readonly name = "vercel";
|
|
233
|
+
private readonly model;
|
|
234
|
+
constructor(config: VercelLLMAdapterConfig);
|
|
235
|
+
chat(messages: ModelMessage[], options?: AIRequestOptions): Promise<AIResult>;
|
|
236
|
+
complete(prompt: string, options?: AIRequestOptions): Promise<AIResult>;
|
|
237
|
+
streamChat(messages: ModelMessage[], options?: AIRequestOptions): AsyncIterable<TextStreamPart<ToolSet>>;
|
|
238
|
+
embed(_input: string | string[]): Promise<number[][]>;
|
|
239
|
+
listModels(): Promise<string[]>;
|
|
240
|
+
}
|
|
241
|
+
/**
|
|
242
|
+
* Configuration for the Vercel LLM adapter.
|
|
243
|
+
*/
|
|
244
|
+
interface VercelLLMAdapterConfig {
|
|
245
|
+
/**
|
|
246
|
+
* A Vercel AI SDK–compatible language model instance.
|
|
247
|
+
*
|
|
248
|
+
* @example `openai('gpt-4o')` or `anthropic('claude-sonnet-4-20250514')`
|
|
249
|
+
*/
|
|
250
|
+
model: LanguageModelV2;
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
/**
|
|
254
|
+
* Vercel AI SDK v6 — UI Message Stream Encoder
|
|
255
|
+
*
|
|
256
|
+
* Converts `AsyncIterable<TextStreamPart<ToolSet>>` (the internal ObjectStack
|
|
257
|
+
* streaming format) into the Vercel AI SDK v6 **UI Message Stream Protocol**.
|
|
258
|
+
*
|
|
259
|
+
* Wire format: Server-Sent Events (SSE) with JSON payloads.
|
|
260
|
+
* `data: {"type":"text-delta","id":"0","delta":"Hello"}\n\n`
|
|
261
|
+
*
|
|
262
|
+
* The client-side `DefaultChatTransport` from `ai` v6 uses
|
|
263
|
+
* `parseJsonEventStream` to parse these SSE events.
|
|
264
|
+
*
|
|
265
|
+
* @see https://ai-sdk.dev/docs/ai-sdk-ui/stream-protocol
|
|
266
|
+
*/
|
|
267
|
+
|
|
268
|
+
/**
|
|
269
|
+
* Encode a single `TextStreamPart` event into SSE-formatted UI Message
|
|
270
|
+
* Stream chunk(s).
|
|
271
|
+
*
|
|
272
|
+
* Returns an empty string for event types that have no wire-format mapping.
|
|
273
|
+
*/
|
|
274
|
+
declare function encodeStreamPart(part: TextStreamPart$1<ToolSet$1>): string;
|
|
275
|
+
/**
|
|
276
|
+
* Transform an `AsyncIterable<TextStreamPart>` into an `AsyncIterable<string>`
|
|
277
|
+
* where each yielded string is an SSE-formatted UI Message Stream chunk.
|
|
278
|
+
*
|
|
279
|
+
* Lifecycle order required by the client:
|
|
280
|
+
* start → start-step → text-start → text-delta* → text-end → finish-step → finish → [DONE]
|
|
281
|
+
*/
|
|
282
|
+
declare function encodeVercelDataStream(events: AsyncIterable<TextStreamPart$1<ToolSet$1>>): AsyncIterable<string>;
|
|
283
|
+
|
|
183
284
|
/**
|
|
184
285
|
* InMemoryConversationService — Reference implementation of IAIConversationService.
|
|
185
286
|
*
|
|
@@ -203,7 +304,7 @@ declare class InMemoryConversationService implements IAIConversationService {
|
|
|
203
304
|
limit?: number;
|
|
204
305
|
cursor?: string;
|
|
205
306
|
}): Promise<AIConversation[]>;
|
|
206
|
-
addMessage(conversationId: string, message:
|
|
307
|
+
addMessage(conversationId: string, message: ModelMessage): Promise<AIConversation>;
|
|
207
308
|
delete(conversationId: string): Promise<void>;
|
|
208
309
|
/** Total number of stored conversations. */
|
|
209
310
|
get size(): number;
|
|
@@ -237,7 +338,7 @@ declare class ObjectQLConversationService implements IAIConversationService {
|
|
|
237
338
|
limit?: number;
|
|
238
339
|
cursor?: string;
|
|
239
340
|
}): Promise<AIConversation[]>;
|
|
240
|
-
addMessage(conversationId: string, message:
|
|
341
|
+
addMessage(conversationId: string, message: ModelMessage): Promise<AIConversation>;
|
|
241
342
|
delete(conversationId: string): Promise<void>;
|
|
242
343
|
/**
|
|
243
344
|
* Safely parse a JSON string, returning `undefined` on failure.
|
|
@@ -248,7 +349,7 @@ declare class ObjectQLConversationService implements IAIConversationService {
|
|
|
248
349
|
*/
|
|
249
350
|
private toConversation;
|
|
250
351
|
/**
|
|
251
|
-
* Map a database row to
|
|
352
|
+
* Map a database row to a ModelMessage.
|
|
252
353
|
*/
|
|
253
354
|
private toMessage;
|
|
254
355
|
}
|
|
@@ -284,6 +385,158 @@ declare const DATA_TOOL_DEFINITIONS: AIToolDefinition[];
|
|
|
284
385
|
*/
|
|
285
386
|
declare function registerDataTools(registry: ToolRegistry, context: DataToolContext): void;
|
|
286
387
|
|
|
388
|
+
/**
|
|
389
|
+
* create_object — AI Tool Metadata
|
|
390
|
+
*
|
|
391
|
+
* Creates a new data object (table) with schema validation.
|
|
392
|
+
* Validates snake_case naming for object and initial fields,
|
|
393
|
+
* checks for duplicates, and registers the object definition.
|
|
394
|
+
*/
|
|
395
|
+
declare const createObjectTool: {
|
|
396
|
+
name: string;
|
|
397
|
+
label: string;
|
|
398
|
+
description: string;
|
|
399
|
+
parameters: Record<string, unknown>;
|
|
400
|
+
requiresConfirmation: boolean;
|
|
401
|
+
active: boolean;
|
|
402
|
+
builtIn: boolean;
|
|
403
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
404
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
405
|
+
objectName?: string | undefined;
|
|
406
|
+
permissions?: string[] | undefined;
|
|
407
|
+
};
|
|
408
|
+
|
|
409
|
+
/**
|
|
410
|
+
* add_field — AI Tool Metadata
|
|
411
|
+
*
|
|
412
|
+
* Adds a new field (column) to an existing data object.
|
|
413
|
+
* Validates snake_case for objectName, field name, reference,
|
|
414
|
+
* and select option values before merging into the definition.
|
|
415
|
+
*/
|
|
416
|
+
declare const addFieldTool: {
|
|
417
|
+
name: string;
|
|
418
|
+
label: string;
|
|
419
|
+
description: string;
|
|
420
|
+
parameters: Record<string, unknown>;
|
|
421
|
+
requiresConfirmation: boolean;
|
|
422
|
+
active: boolean;
|
|
423
|
+
builtIn: boolean;
|
|
424
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
425
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
426
|
+
objectName?: string | undefined;
|
|
427
|
+
permissions?: string[] | undefined;
|
|
428
|
+
};
|
|
429
|
+
|
|
430
|
+
/**
|
|
431
|
+
* modify_field — AI Tool Metadata
|
|
432
|
+
*
|
|
433
|
+
* Modifies an existing field definition (label, type, required, default value, etc.)
|
|
434
|
+
* on a data object. Does not support renaming the field.
|
|
435
|
+
*/
|
|
436
|
+
declare const modifyFieldTool: {
|
|
437
|
+
name: string;
|
|
438
|
+
label: string;
|
|
439
|
+
description: string;
|
|
440
|
+
parameters: Record<string, unknown>;
|
|
441
|
+
requiresConfirmation: boolean;
|
|
442
|
+
active: boolean;
|
|
443
|
+
builtIn: boolean;
|
|
444
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
445
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
446
|
+
objectName?: string | undefined;
|
|
447
|
+
permissions?: string[] | undefined;
|
|
448
|
+
};
|
|
449
|
+
|
|
450
|
+
/**
|
|
451
|
+
* delete_field — AI Tool Metadata
|
|
452
|
+
*
|
|
453
|
+
* Removes a field (column) from an existing data object.
|
|
454
|
+
* This is a destructive operation.
|
|
455
|
+
*/
|
|
456
|
+
declare const deleteFieldTool: {
|
|
457
|
+
name: string;
|
|
458
|
+
label: string;
|
|
459
|
+
description: string;
|
|
460
|
+
parameters: Record<string, unknown>;
|
|
461
|
+
requiresConfirmation: boolean;
|
|
462
|
+
active: boolean;
|
|
463
|
+
builtIn: boolean;
|
|
464
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
465
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
466
|
+
objectName?: string | undefined;
|
|
467
|
+
permissions?: string[] | undefined;
|
|
468
|
+
};
|
|
469
|
+
|
|
470
|
+
/**
|
|
471
|
+
* list_metadata_objects — AI Tool Metadata
|
|
472
|
+
*
|
|
473
|
+
* Lists all registered metadata objects (tables) with optional filtering.
|
|
474
|
+
* Uses a unique name (`list_metadata_objects`) to avoid collision with
|
|
475
|
+
* the data-tools `list_objects` tool.
|
|
476
|
+
*/
|
|
477
|
+
declare const listMetadataObjectsTool: {
|
|
478
|
+
name: string;
|
|
479
|
+
label: string;
|
|
480
|
+
description: string;
|
|
481
|
+
parameters: Record<string, unknown>;
|
|
482
|
+
requiresConfirmation: boolean;
|
|
483
|
+
active: boolean;
|
|
484
|
+
builtIn: boolean;
|
|
485
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
486
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
487
|
+
objectName?: string | undefined;
|
|
488
|
+
permissions?: string[] | undefined;
|
|
489
|
+
};
|
|
490
|
+
|
|
491
|
+
/**
|
|
492
|
+
* describe_metadata_object — AI Tool Metadata
|
|
493
|
+
*
|
|
494
|
+
* Returns the full metadata schema of a data object including all
|
|
495
|
+
* fields, types, relationships, and configuration. Uses a unique name
|
|
496
|
+
* (`describe_metadata_object`) to avoid collision with the data-tools
|
|
497
|
+
* `describe_object` tool.
|
|
498
|
+
*/
|
|
499
|
+
declare const describeMetadataObjectTool: {
|
|
500
|
+
name: string;
|
|
501
|
+
label: string;
|
|
502
|
+
description: string;
|
|
503
|
+
parameters: Record<string, unknown>;
|
|
504
|
+
requiresConfirmation: boolean;
|
|
505
|
+
active: boolean;
|
|
506
|
+
builtIn: boolean;
|
|
507
|
+
category?: "flow" | "action" | "vector_search" | "data" | "utility" | "integration" | "analytics" | undefined;
|
|
508
|
+
outputSchema?: Record<string, unknown> | undefined;
|
|
509
|
+
objectName?: string | undefined;
|
|
510
|
+
permissions?: string[] | undefined;
|
|
511
|
+
};
|
|
512
|
+
|
|
513
|
+
/** All built-in metadata management tool definitions (Tool metadata). */
|
|
514
|
+
declare const METADATA_TOOL_DEFINITIONS: Tool[];
|
|
515
|
+
/**
|
|
516
|
+
* Services required by the metadata management tools.
|
|
517
|
+
*
|
|
518
|
+
* Provided by the kernel at `ai:ready` time and closed over
|
|
519
|
+
* by the handler functions so they stay framework-agnostic.
|
|
520
|
+
*/
|
|
521
|
+
interface MetadataToolContext {
|
|
522
|
+
/** Metadata service for schema CRUD operations. */
|
|
523
|
+
metadataService: IMetadataService;
|
|
524
|
+
}
|
|
525
|
+
/**
|
|
526
|
+
* Register all built-in metadata management tools on the given {@link ToolRegistry}.
|
|
527
|
+
*
|
|
528
|
+
* Typically called from the `ai:ready` hook after the metadata service is available.
|
|
529
|
+
*
|
|
530
|
+
* @example
|
|
531
|
+
* ```ts
|
|
532
|
+
* ctx.hook('ai:ready', async (aiService) => {
|
|
533
|
+
* const metadataService = ctx.getService<IMetadataService>('metadata');
|
|
534
|
+
* registerMetadataTools(aiService.toolRegistry, { metadataService });
|
|
535
|
+
* });
|
|
536
|
+
* ```
|
|
537
|
+
*/
|
|
538
|
+
declare function registerMetadataTools(registry: ToolRegistry, context: MetadataToolContext): void;
|
|
539
|
+
|
|
287
540
|
/**
|
|
288
541
|
* Context passed alongside a user message when chatting with an agent.
|
|
289
542
|
*
|
|
@@ -312,6 +565,17 @@ interface AgentChatContext {
|
|
|
312
565
|
declare class AgentRuntime {
|
|
313
566
|
private readonly metadataService;
|
|
314
567
|
constructor(metadataService: IMetadataService);
|
|
568
|
+
/**
|
|
569
|
+
* List all active agents registered in the metadata service.
|
|
570
|
+
*
|
|
571
|
+
* Returns a summary for each agent (name, label, role) suitable
|
|
572
|
+
* for populating an agent selector dropdown in the UI.
|
|
573
|
+
*/
|
|
574
|
+
listAgents(): Promise<Array<{
|
|
575
|
+
name: string;
|
|
576
|
+
label: string;
|
|
577
|
+
role: string;
|
|
578
|
+
}>>;
|
|
315
579
|
/**
|
|
316
580
|
* Load and validate an agent definition by name.
|
|
317
581
|
*
|
|
@@ -325,7 +589,7 @@ declare class AgentRuntime {
|
|
|
325
589
|
* Build the system message(s) that should be prepended to the
|
|
326
590
|
* conversation when chatting with the given agent.
|
|
327
591
|
*/
|
|
328
|
-
buildSystemMessages(agent: Agent, context?: AgentChatContext):
|
|
592
|
+
buildSystemMessages(agent: Agent, context?: AgentChatContext): ModelMessage[];
|
|
329
593
|
/**
|
|
330
594
|
* Derive {@link AIRequestOptions} from an agent definition.
|
|
331
595
|
*
|
|
@@ -360,6 +624,27 @@ declare class AgentRuntime {
|
|
|
360
624
|
*/
|
|
361
625
|
declare const DATA_CHAT_AGENT: Agent;
|
|
362
626
|
|
|
627
|
+
/**
|
|
628
|
+
* Built-in `metadata_assistant` agent definition.
|
|
629
|
+
*
|
|
630
|
+
* This agent powers AI-driven metadata management — users can create objects,
|
|
631
|
+
* add/modify/delete fields, and inspect schema definitions through natural
|
|
632
|
+
* language conversation.
|
|
633
|
+
*
|
|
634
|
+
* It is registered automatically by the AI service plugin alongside the
|
|
635
|
+
* `data_chat` agent when the metadata service is available.
|
|
636
|
+
*
|
|
637
|
+
* @example
|
|
638
|
+
* ```
|
|
639
|
+
* POST /api/v1/ai/agents/metadata_assistant/chat
|
|
640
|
+
* {
|
|
641
|
+
* "messages": [{ "role": "user", "content": "Create a contracts table with name, value, and status fields" }],
|
|
642
|
+
* "context": {}
|
|
643
|
+
* }
|
|
644
|
+
* ```
|
|
645
|
+
*/
|
|
646
|
+
declare const METADATA_ASSISTANT_AGENT: Agent;
|
|
647
|
+
|
|
363
648
|
/**
|
|
364
649
|
* XState-inspired State Machine Protocol
|
|
365
650
|
* Used to define strict business logic constraints and lifecycle management.
|
|
@@ -423,7 +708,7 @@ declare const AiConversationObject: Omit<{
|
|
|
423
708
|
abstract: boolean;
|
|
424
709
|
datasource: string;
|
|
425
710
|
fields: Record<string, {
|
|
426
|
-
type: "number" | "boolean" | "file" | "json" | "
|
|
711
|
+
type: "number" | "boolean" | "file" | "text" | "json" | "code" | "avatar" | "vector" | "date" | "tags" | "lookup" | "url" | "textarea" | "email" | "phone" | "password" | "markdown" | "html" | "richtext" | "currency" | "percent" | "datetime" | "time" | "toggle" | "select" | "multiselect" | "radio" | "checkboxes" | "master_detail" | "tree" | "image" | "video" | "audio" | "formula" | "summary" | "autonumber" | "location" | "address" | "color" | "rating" | "slider" | "signature" | "qrcode" | "progress";
|
|
427
712
|
required: boolean;
|
|
428
713
|
searchable: boolean;
|
|
429
714
|
multiple: boolean;
|
|
@@ -607,7 +892,7 @@ declare const AiConversationObject: Omit<{
|
|
|
607
892
|
} | undefined;
|
|
608
893
|
versioning?: {
|
|
609
894
|
enabled: boolean;
|
|
610
|
-
strategy: "
|
|
895
|
+
strategy: "delta" | "snapshot" | "event-sourcing";
|
|
611
896
|
versionField: string;
|
|
612
897
|
retentionDays?: number | undefined;
|
|
613
898
|
} | undefined;
|
|
@@ -683,11 +968,7 @@ declare const AiConversationObject: Omit<{
|
|
|
683
968
|
keyPrefix?: string | undefined;
|
|
684
969
|
actions?: {
|
|
685
970
|
name: string;
|
|
686
|
-
label: string
|
|
687
|
-
key: string;
|
|
688
|
-
defaultValue?: string | undefined;
|
|
689
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
690
|
-
};
|
|
971
|
+
label: string;
|
|
691
972
|
type: "url" | "script" | "modal" | "flow" | "api";
|
|
692
973
|
refreshAfter: boolean;
|
|
693
974
|
objectName?: string | undefined;
|
|
@@ -698,44 +979,24 @@ declare const AiConversationObject: Omit<{
|
|
|
698
979
|
execute?: string | undefined;
|
|
699
980
|
params?: {
|
|
700
981
|
name: string;
|
|
701
|
-
label: string
|
|
702
|
-
key: string;
|
|
703
|
-
defaultValue?: string | undefined;
|
|
704
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
705
|
-
};
|
|
982
|
+
label: string;
|
|
706
983
|
type: "number" | "boolean" | "date" | "lookup" | "file" | "url" | "json" | "text" | "textarea" | "email" | "phone" | "password" | "markdown" | "html" | "richtext" | "currency" | "percent" | "datetime" | "time" | "toggle" | "select" | "multiselect" | "radio" | "checkboxes" | "master_detail" | "tree" | "image" | "avatar" | "video" | "audio" | "formula" | "summary" | "autonumber" | "location" | "address" | "code" | "color" | "rating" | "slider" | "signature" | "qrcode" | "progress" | "tags" | "vector";
|
|
707
984
|
required: boolean;
|
|
708
985
|
options?: {
|
|
709
|
-
label: string
|
|
710
|
-
key: string;
|
|
711
|
-
defaultValue?: string | undefined;
|
|
712
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
713
|
-
};
|
|
986
|
+
label: string;
|
|
714
987
|
value: string;
|
|
715
988
|
}[] | undefined;
|
|
716
989
|
}[] | undefined;
|
|
717
990
|
variant?: "link" | "primary" | "secondary" | "danger" | "ghost" | undefined;
|
|
718
|
-
confirmText?: string |
|
|
719
|
-
|
|
720
|
-
defaultValue?: string | undefined;
|
|
721
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
722
|
-
} | undefined;
|
|
723
|
-
successMessage?: string | {
|
|
724
|
-
key: string;
|
|
725
|
-
defaultValue?: string | undefined;
|
|
726
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
727
|
-
} | undefined;
|
|
991
|
+
confirmText?: string | undefined;
|
|
992
|
+
successMessage?: string | undefined;
|
|
728
993
|
visible?: string | undefined;
|
|
729
994
|
disabled?: string | boolean | undefined;
|
|
730
995
|
shortcut?: string | undefined;
|
|
731
996
|
bulkEnabled?: boolean | undefined;
|
|
732
997
|
timeout?: number | undefined;
|
|
733
998
|
aria?: {
|
|
734
|
-
ariaLabel?: string |
|
|
735
|
-
key: string;
|
|
736
|
-
defaultValue?: string | undefined;
|
|
737
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
738
|
-
} | undefined;
|
|
999
|
+
ariaLabel?: string | undefined;
|
|
739
1000
|
ariaDescribedBy?: string | undefined;
|
|
740
1001
|
role?: string | undefined;
|
|
741
1002
|
} | undefined;
|
|
@@ -1888,7 +2149,7 @@ declare const AiMessageObject: Omit<{
|
|
|
1888
2149
|
abstract: boolean;
|
|
1889
2150
|
datasource: string;
|
|
1890
2151
|
fields: Record<string, {
|
|
1891
|
-
type: "number" | "boolean" | "file" | "json" | "
|
|
2152
|
+
type: "number" | "boolean" | "file" | "text" | "json" | "code" | "avatar" | "vector" | "date" | "tags" | "lookup" | "url" | "textarea" | "email" | "phone" | "password" | "markdown" | "html" | "richtext" | "currency" | "percent" | "datetime" | "time" | "toggle" | "select" | "multiselect" | "radio" | "checkboxes" | "master_detail" | "tree" | "image" | "video" | "audio" | "formula" | "summary" | "autonumber" | "location" | "address" | "color" | "rating" | "slider" | "signature" | "qrcode" | "progress";
|
|
1892
2153
|
required: boolean;
|
|
1893
2154
|
searchable: boolean;
|
|
1894
2155
|
multiple: boolean;
|
|
@@ -2072,7 +2333,7 @@ declare const AiMessageObject: Omit<{
|
|
|
2072
2333
|
} | undefined;
|
|
2073
2334
|
versioning?: {
|
|
2074
2335
|
enabled: boolean;
|
|
2075
|
-
strategy: "
|
|
2336
|
+
strategy: "delta" | "snapshot" | "event-sourcing";
|
|
2076
2337
|
versionField: string;
|
|
2077
2338
|
retentionDays?: number | undefined;
|
|
2078
2339
|
} | undefined;
|
|
@@ -2148,11 +2409,7 @@ declare const AiMessageObject: Omit<{
|
|
|
2148
2409
|
keyPrefix?: string | undefined;
|
|
2149
2410
|
actions?: {
|
|
2150
2411
|
name: string;
|
|
2151
|
-
label: string
|
|
2152
|
-
key: string;
|
|
2153
|
-
defaultValue?: string | undefined;
|
|
2154
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2155
|
-
};
|
|
2412
|
+
label: string;
|
|
2156
2413
|
type: "url" | "script" | "modal" | "flow" | "api";
|
|
2157
2414
|
refreshAfter: boolean;
|
|
2158
2415
|
objectName?: string | undefined;
|
|
@@ -2163,44 +2420,24 @@ declare const AiMessageObject: Omit<{
|
|
|
2163
2420
|
execute?: string | undefined;
|
|
2164
2421
|
params?: {
|
|
2165
2422
|
name: string;
|
|
2166
|
-
label: string
|
|
2167
|
-
key: string;
|
|
2168
|
-
defaultValue?: string | undefined;
|
|
2169
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2170
|
-
};
|
|
2423
|
+
label: string;
|
|
2171
2424
|
type: "number" | "boolean" | "date" | "lookup" | "file" | "url" | "json" | "text" | "textarea" | "email" | "phone" | "password" | "markdown" | "html" | "richtext" | "currency" | "percent" | "datetime" | "time" | "toggle" | "select" | "multiselect" | "radio" | "checkboxes" | "master_detail" | "tree" | "image" | "avatar" | "video" | "audio" | "formula" | "summary" | "autonumber" | "location" | "address" | "code" | "color" | "rating" | "slider" | "signature" | "qrcode" | "progress" | "tags" | "vector";
|
|
2172
2425
|
required: boolean;
|
|
2173
2426
|
options?: {
|
|
2174
|
-
label: string
|
|
2175
|
-
key: string;
|
|
2176
|
-
defaultValue?: string | undefined;
|
|
2177
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2178
|
-
};
|
|
2427
|
+
label: string;
|
|
2179
2428
|
value: string;
|
|
2180
2429
|
}[] | undefined;
|
|
2181
2430
|
}[] | undefined;
|
|
2182
2431
|
variant?: "link" | "primary" | "secondary" | "danger" | "ghost" | undefined;
|
|
2183
|
-
confirmText?: string |
|
|
2184
|
-
|
|
2185
|
-
defaultValue?: string | undefined;
|
|
2186
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2187
|
-
} | undefined;
|
|
2188
|
-
successMessage?: string | {
|
|
2189
|
-
key: string;
|
|
2190
|
-
defaultValue?: string | undefined;
|
|
2191
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2192
|
-
} | undefined;
|
|
2432
|
+
confirmText?: string | undefined;
|
|
2433
|
+
successMessage?: string | undefined;
|
|
2193
2434
|
visible?: string | undefined;
|
|
2194
2435
|
disabled?: string | boolean | undefined;
|
|
2195
2436
|
shortcut?: string | undefined;
|
|
2196
2437
|
bulkEnabled?: boolean | undefined;
|
|
2197
2438
|
timeout?: number | undefined;
|
|
2198
2439
|
aria?: {
|
|
2199
|
-
ariaLabel?: string |
|
|
2200
|
-
key: string;
|
|
2201
|
-
defaultValue?: string | undefined;
|
|
2202
|
-
params?: Record<string, string | number | boolean> | undefined;
|
|
2203
|
-
} | undefined;
|
|
2440
|
+
ariaLabel?: string | undefined;
|
|
2204
2441
|
ariaDescribedBy?: string | undefined;
|
|
2205
2442
|
role?: string | undefined;
|
|
2206
2443
|
} | undefined;
|
|
@@ -3349,12 +3586,31 @@ interface RouteDefinition {
|
|
|
3349
3586
|
path: string;
|
|
3350
3587
|
/** Human-readable description */
|
|
3351
3588
|
description: string;
|
|
3589
|
+
/** Whether this route requires authentication (default: true). */
|
|
3590
|
+
auth?: boolean;
|
|
3591
|
+
/** Required permissions for accessing this route. */
|
|
3592
|
+
permissions?: string[];
|
|
3352
3593
|
/**
|
|
3353
3594
|
* Handler receives a plain request-like object and returns a response-like
|
|
3354
3595
|
* object. SSE responses set `stream: true` and provide an async iterable.
|
|
3355
3596
|
*/
|
|
3356
3597
|
handler: (req: RouteRequest) => Promise<RouteResponse>;
|
|
3357
3598
|
}
|
|
3599
|
+
/**
|
|
3600
|
+
* Authenticated user context attached to a route request.
|
|
3601
|
+
*
|
|
3602
|
+
* Populated by the auth middleware when `RouteDefinition.auth` is `true`.
|
|
3603
|
+
*/
|
|
3604
|
+
interface RouteUserContext {
|
|
3605
|
+
/** Unique user identifier. */
|
|
3606
|
+
userId: string;
|
|
3607
|
+
/** User display name (optional). */
|
|
3608
|
+
displayName?: string;
|
|
3609
|
+
/** Roles assigned to the user (e.g. `['admin', 'user']`). */
|
|
3610
|
+
roles?: string[];
|
|
3611
|
+
/** Fine-grained permissions (e.g. `['ai:chat', 'ai:admin']`). */
|
|
3612
|
+
permissions?: string[];
|
|
3613
|
+
}
|
|
3358
3614
|
interface RouteRequest {
|
|
3359
3615
|
/** Parsed JSON body (for POST requests) */
|
|
3360
3616
|
body?: unknown;
|
|
@@ -3362,6 +3618,8 @@ interface RouteRequest {
|
|
|
3362
3618
|
params?: Record<string, string>;
|
|
3363
3619
|
/** Query string parameters */
|
|
3364
3620
|
query?: Record<string, string>;
|
|
3621
|
+
/** Authenticated user context (populated by auth middleware). */
|
|
3622
|
+
user?: RouteUserContext;
|
|
3365
3623
|
}
|
|
3366
3624
|
interface RouteResponse {
|
|
3367
3625
|
/** HTTP status code */
|
|
@@ -3372,6 +3630,14 @@ interface RouteResponse {
|
|
|
3372
3630
|
stream?: boolean;
|
|
3373
3631
|
/** Async iterable of SSE events (when stream=true) */
|
|
3374
3632
|
events?: AsyncIterable<unknown>;
|
|
3633
|
+
/**
|
|
3634
|
+
* When `true`, the HTTP server layer should encode the `events` iterable
|
|
3635
|
+
* using the Vercel AI Data Stream Protocol frame format (`0:`, `9:`, `d:`, …)
|
|
3636
|
+
* instead of generic SSE `data:` lines.
|
|
3637
|
+
*
|
|
3638
|
+
* @see https://ai-sdk.dev/docs/ai-sdk-ui/stream-protocol
|
|
3639
|
+
*/
|
|
3640
|
+
vercelDataStream?: boolean;
|
|
3375
3641
|
}
|
|
3376
3642
|
/**
|
|
3377
3643
|
* Build the standard AI REST/SSE routes.
|
|
@@ -3399,8 +3665,9 @@ declare function buildAIRoutes(aiService: IAIService, conversationService: IAICo
|
|
|
3399
3665
|
*
|
|
3400
3666
|
* | Method | Path | Description |
|
|
3401
3667
|
* |:---|:---|:---|
|
|
3668
|
+
* | GET | /api/v1/ai/agents | List all active agents |
|
|
3402
3669
|
* | POST | /api/v1/ai/agents/:agentName/chat | Chat with a specific agent |
|
|
3403
3670
|
*/
|
|
3404
3671
|
declare function buildAgentRoutes(aiService: AIService, agentRuntime: AgentRuntime, logger: Logger): RouteDefinition[];
|
|
3405
3672
|
|
|
3406
|
-
export { AIService, type AIServiceConfig, AIServicePlugin, type AIServicePluginOptions, type AgentChatContext, AgentRuntime, AiConversationObject, AiMessageObject, DATA_CHAT_AGENT, DATA_TOOL_DEFINITIONS, type DataToolContext, InMemoryConversationService, MemoryLLMAdapter, ObjectQLConversationService, type RouteDefinition, type RouteRequest, type RouteResponse, type ToolHandler, ToolRegistry, buildAIRoutes, buildAgentRoutes, registerDataTools };
|
|
3673
|
+
export { AIService, type AIServiceConfig, AIServicePlugin, type AIServicePluginOptions, type AgentChatContext, AgentRuntime, AiConversationObject, AiMessageObject, DATA_CHAT_AGENT, DATA_TOOL_DEFINITIONS, type DataToolContext, InMemoryConversationService, METADATA_ASSISTANT_AGENT, METADATA_TOOL_DEFINITIONS, MemoryLLMAdapter, type MetadataToolContext, ObjectQLConversationService, type RouteDefinition, type RouteRequest, type RouteResponse, type RouteUserContext, type ToolExecutionResult, type ToolHandler, ToolRegistry, VercelLLMAdapter, type VercelLLMAdapterConfig, addFieldTool, buildAIRoutes, buildAgentRoutes, createObjectTool, deleteFieldTool, describeMetadataObjectTool, encodeStreamPart, encodeVercelDataStream, listMetadataObjectsTool, modifyFieldTool, registerDataTools, registerMetadataTools };
|