dominus-sdk-nodejs 1.2.44 → 1.3.1
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/dist/index.d.ts +4 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +4 -0
- package/dist/index.js.map +1 -1
- package/dist/lib/client.d.ts +44 -1
- package/dist/lib/client.d.ts.map +1 -1
- package/dist/lib/client.js +215 -5
- package/dist/lib/client.js.map +1 -1
- package/dist/lib/config.d.ts +2 -1
- package/dist/lib/config.d.ts.map +1 -1
- package/dist/lib/config.js +5 -1
- package/dist/lib/config.js.map +1 -1
- package/dist/namespaces/ai.d.ts +349 -0
- package/dist/namespaces/ai.d.ts.map +1 -0
- package/dist/namespaces/ai.js +683 -0
- package/dist/namespaces/ai.js.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,683 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* AI Namespace - Unified agent-runtime operations.
|
|
3
|
+
*
|
|
4
|
+
* Provides agent execution, LLM completions, RAG corpus management,
|
|
5
|
+
* artifacts, speech services, and workflow orchestration.
|
|
6
|
+
*
|
|
7
|
+
* All operations go through /api/* endpoints on the agent-runtime service,
|
|
8
|
+
* proxied via the gateway at /svc/*.
|
|
9
|
+
*
|
|
10
|
+
* Usage:
|
|
11
|
+
* import { dominus } from 'dominus-sdk-nodejs';
|
|
12
|
+
*
|
|
13
|
+
* // Agent execution
|
|
14
|
+
* const result = await dominus.ai.runAgent({
|
|
15
|
+
* conversationId: "conv-123",
|
|
16
|
+
* systemPrompt: "You are helpful.",
|
|
17
|
+
* userPrompt: "Hello!"
|
|
18
|
+
* });
|
|
19
|
+
*
|
|
20
|
+
* // Streaming agent execution
|
|
21
|
+
* for await (const chunk of dominus.ai.streamAgent({
|
|
22
|
+
* conversationId: "conv-123",
|
|
23
|
+
* systemPrompt: "You are helpful.",
|
|
24
|
+
* userPrompt: "Tell me a story"
|
|
25
|
+
* })) {
|
|
26
|
+
* process.stdout.write(chunk.content || '');
|
|
27
|
+
* }
|
|
28
|
+
*
|
|
29
|
+
* // LLM completion
|
|
30
|
+
* const result = await dominus.ai.complete({
|
|
31
|
+
* messages: [{ role: "user", content: "Hello" }],
|
|
32
|
+
* provider: "claude",
|
|
33
|
+
* model: "claude-sonnet-4-5"
|
|
34
|
+
* });
|
|
35
|
+
*
|
|
36
|
+
* // RAG operations
|
|
37
|
+
* await dominus.ai.rag.ensure("my-corpus");
|
|
38
|
+
* await dominus.ai.rag.upsert("my-corpus", "doc-1", { content: "Important info" });
|
|
39
|
+
* const results = await dominus.ai.rag.search("my-corpus", "important");
|
|
40
|
+
*
|
|
41
|
+
* // Speech
|
|
42
|
+
* const text = await dominus.ai.stt(audioBuffer, { format: "wav" });
|
|
43
|
+
* const audio = await dominus.ai.tts("Hello world", { voice: "nova" });
|
|
44
|
+
*/
|
|
45
|
+
// ============================================================================
|
|
46
|
+
// Helper Functions
|
|
47
|
+
// ============================================================================
|
|
48
|
+
/**
|
|
49
|
+
* Convert snake_case keys to camelCase in an object (shallow)
|
|
50
|
+
*/
|
|
51
|
+
function snakeToCamel(str) {
|
|
52
|
+
return str.replace(/_([a-z])/g, (_, letter) => letter.toUpperCase());
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Normalize response object keys from snake_case to camelCase
|
|
56
|
+
*/
|
|
57
|
+
function normalizeResponse(obj) {
|
|
58
|
+
const result = {};
|
|
59
|
+
for (const [key, value] of Object.entries(obj)) {
|
|
60
|
+
const camelKey = snakeToCamel(key);
|
|
61
|
+
result[camelKey] = value;
|
|
62
|
+
// Also keep original key for backward compatibility
|
|
63
|
+
if (camelKey !== key) {
|
|
64
|
+
result[key] = value;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return result;
|
|
68
|
+
}
|
|
69
|
+
// ============================================================================
|
|
70
|
+
// RAG Sub-namespace
|
|
71
|
+
// ============================================================================
|
|
72
|
+
export class RagSubNamespace {
|
|
73
|
+
client;
|
|
74
|
+
constructor(client) {
|
|
75
|
+
this.client = client;
|
|
76
|
+
}
|
|
77
|
+
/** List all corpora */
|
|
78
|
+
async list() {
|
|
79
|
+
const result = await this.client.request({
|
|
80
|
+
endpoint: '/api/rag',
|
|
81
|
+
method: 'GET',
|
|
82
|
+
useGateway: true,
|
|
83
|
+
});
|
|
84
|
+
if (Array.isArray(result))
|
|
85
|
+
return result;
|
|
86
|
+
return result.corpora || [];
|
|
87
|
+
}
|
|
88
|
+
/** Ensure corpus exists (create if not) */
|
|
89
|
+
async ensure(slug, options) {
|
|
90
|
+
const body = {};
|
|
91
|
+
if (options?.description)
|
|
92
|
+
body.description = options.description;
|
|
93
|
+
if (options?.embeddingModel)
|
|
94
|
+
body.embedding_model = options.embeddingModel;
|
|
95
|
+
return this.client.request({
|
|
96
|
+
endpoint: `/api/rag/${slug}/ensure`,
|
|
97
|
+
body,
|
|
98
|
+
useGateway: true,
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
/** Get corpus statistics */
|
|
102
|
+
async stats(slug) {
|
|
103
|
+
return this.client.request({
|
|
104
|
+
endpoint: `/api/rag/${slug}/stats`,
|
|
105
|
+
method: 'GET',
|
|
106
|
+
useGateway: true,
|
|
107
|
+
});
|
|
108
|
+
}
|
|
109
|
+
/** Drop/delete a corpus */
|
|
110
|
+
async drop(slug) {
|
|
111
|
+
return this.client.request({
|
|
112
|
+
endpoint: `/api/rag/${slug}`,
|
|
113
|
+
method: 'DELETE',
|
|
114
|
+
useGateway: true,
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
/** List entries in a corpus */
|
|
118
|
+
async entries(slug, options) {
|
|
119
|
+
return this.client.request({
|
|
120
|
+
endpoint: `/api/rag/${slug}/entries`,
|
|
121
|
+
body: {
|
|
122
|
+
limit: options?.limit ?? 100,
|
|
123
|
+
offset: options?.offset ?? 0,
|
|
124
|
+
...(options?.category && { category: options.category }),
|
|
125
|
+
},
|
|
126
|
+
useGateway: true,
|
|
127
|
+
});
|
|
128
|
+
}
|
|
129
|
+
/** Upsert a single entry */
|
|
130
|
+
async upsert(slug, identifier, options) {
|
|
131
|
+
const body = {
|
|
132
|
+
content_markdown: options.content, // Transform: content -> content_markdown
|
|
133
|
+
};
|
|
134
|
+
if (options.name)
|
|
135
|
+
body.name = options.name;
|
|
136
|
+
if (options.description)
|
|
137
|
+
body.description = options.description;
|
|
138
|
+
if (options.category)
|
|
139
|
+
body.category = options.category;
|
|
140
|
+
if (options.subcategory)
|
|
141
|
+
body.subcategory = options.subcategory;
|
|
142
|
+
if (options.sourceReference)
|
|
143
|
+
body.source_reference = options.sourceReference;
|
|
144
|
+
if (options.metadata)
|
|
145
|
+
body.metadata = options.metadata;
|
|
146
|
+
return this.client.request({
|
|
147
|
+
endpoint: `/api/rag/${slug}/${identifier}`,
|
|
148
|
+
method: 'PUT',
|
|
149
|
+
body,
|
|
150
|
+
useGateway: true,
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
/** Get a specific entry */
|
|
154
|
+
async get(slug, identifier) {
|
|
155
|
+
return this.client.request({
|
|
156
|
+
endpoint: `/api/rag/${slug}/${identifier}`,
|
|
157
|
+
method: 'GET',
|
|
158
|
+
useGateway: true,
|
|
159
|
+
});
|
|
160
|
+
}
|
|
161
|
+
/** Delete an entry */
|
|
162
|
+
async delete(slug, identifier) {
|
|
163
|
+
return this.client.request({
|
|
164
|
+
endpoint: `/api/rag/${slug}/${identifier}`,
|
|
165
|
+
method: 'DELETE',
|
|
166
|
+
useGateway: true,
|
|
167
|
+
});
|
|
168
|
+
}
|
|
169
|
+
/** Bulk upsert entries */
|
|
170
|
+
async bulkUpsert(slug, entries) {
|
|
171
|
+
// Transform 'content' to 'content_markdown' for API compatibility
|
|
172
|
+
const transformed = entries.map((entry) => {
|
|
173
|
+
const e = { ...entry };
|
|
174
|
+
if (e.content && !e.content_markdown) {
|
|
175
|
+
e.content_markdown = e.content;
|
|
176
|
+
delete e.content;
|
|
177
|
+
}
|
|
178
|
+
return e;
|
|
179
|
+
});
|
|
180
|
+
return this.client.request({
|
|
181
|
+
endpoint: `/api/rag/${slug}/bulk`,
|
|
182
|
+
body: { entries: transformed },
|
|
183
|
+
useGateway: true,
|
|
184
|
+
});
|
|
185
|
+
}
|
|
186
|
+
/** Semantic search */
|
|
187
|
+
async search(slug, query, options) {
|
|
188
|
+
const body = {
|
|
189
|
+
query,
|
|
190
|
+
limit: options?.limit ?? 10,
|
|
191
|
+
};
|
|
192
|
+
if (options?.threshold !== undefined)
|
|
193
|
+
body.threshold = options.threshold;
|
|
194
|
+
if (options?.category)
|
|
195
|
+
body.category = options.category;
|
|
196
|
+
if (options?.filters)
|
|
197
|
+
body.filters = options.filters;
|
|
198
|
+
const result = await this.client.request({
|
|
199
|
+
endpoint: `/api/rag/${slug}/search`,
|
|
200
|
+
body,
|
|
201
|
+
useGateway: true,
|
|
202
|
+
});
|
|
203
|
+
if (Array.isArray(result))
|
|
204
|
+
return result;
|
|
205
|
+
return result.results || [];
|
|
206
|
+
}
|
|
207
|
+
/** Semantic search with reranking */
|
|
208
|
+
async searchRerank(slug, query, options) {
|
|
209
|
+
const body = {
|
|
210
|
+
query,
|
|
211
|
+
limit: options?.limit ?? 10,
|
|
212
|
+
};
|
|
213
|
+
if (options?.rerankModel)
|
|
214
|
+
body.rerank_model = options.rerankModel;
|
|
215
|
+
const result = await this.client.request({
|
|
216
|
+
endpoint: `/api/rag/${slug}/search/rerank`,
|
|
217
|
+
body,
|
|
218
|
+
useGateway: true,
|
|
219
|
+
});
|
|
220
|
+
if (Array.isArray(result))
|
|
221
|
+
return result;
|
|
222
|
+
return result.results || [];
|
|
223
|
+
}
|
|
224
|
+
/** Ingest a document (PDF, DOCX, etc.) */
|
|
225
|
+
async ingest(slug, content, filename, options) {
|
|
226
|
+
return this.client.binaryUpload({
|
|
227
|
+
endpoint: `/api/rag/${slug}/ingest`,
|
|
228
|
+
fileBytes: content,
|
|
229
|
+
filename,
|
|
230
|
+
contentType: options?.contentType || 'application/octet-stream',
|
|
231
|
+
additionalFields: {
|
|
232
|
+
chunk_size: String(options?.chunkSize ?? 1000),
|
|
233
|
+
chunk_overlap: String(options?.chunkOverlap ?? 200),
|
|
234
|
+
},
|
|
235
|
+
useGateway: true,
|
|
236
|
+
});
|
|
237
|
+
}
|
|
238
|
+
/** Delete a document and all its chunks */
|
|
239
|
+
async deleteDocument(slug, documentId) {
|
|
240
|
+
return this.client.request({
|
|
241
|
+
endpoint: `/api/rag/${slug}/document/${documentId}`,
|
|
242
|
+
method: 'DELETE',
|
|
243
|
+
useGateway: true,
|
|
244
|
+
});
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
// ============================================================================
|
|
248
|
+
// Artifacts Sub-namespace
|
|
249
|
+
// ============================================================================
|
|
250
|
+
export class ArtifactsSubNamespace {
|
|
251
|
+
client;
|
|
252
|
+
constructor(client) {
|
|
253
|
+
this.client = client;
|
|
254
|
+
}
|
|
255
|
+
/** Get artifact by ID */
|
|
256
|
+
async get(artifactId, conversationId) {
|
|
257
|
+
return this.client.request({
|
|
258
|
+
endpoint: `/api/agent/artifacts/${artifactId}?conversation_id=${conversationId}`,
|
|
259
|
+
method: 'GET',
|
|
260
|
+
useGateway: true,
|
|
261
|
+
});
|
|
262
|
+
}
|
|
263
|
+
/** Create a new artifact */
|
|
264
|
+
async create(options) {
|
|
265
|
+
return this.client.request({
|
|
266
|
+
endpoint: '/api/agent/artifacts',
|
|
267
|
+
body: {
|
|
268
|
+
key: options.name, // Transform: name -> key
|
|
269
|
+
content: options.content,
|
|
270
|
+
conversation_id: options.conversationId,
|
|
271
|
+
content_type: options.artifactType || 'text/plain', // Transform: artifactType -> content_type
|
|
272
|
+
is_base64: options.isBase64 || false,
|
|
273
|
+
},
|
|
274
|
+
useGateway: true,
|
|
275
|
+
});
|
|
276
|
+
}
|
|
277
|
+
/** List artifacts for a conversation */
|
|
278
|
+
async list(conversationId) {
|
|
279
|
+
const result = await this.client.request({
|
|
280
|
+
endpoint: `/api/agent/artifacts?conversation_id=${conversationId}`,
|
|
281
|
+
method: 'GET',
|
|
282
|
+
useGateway: true,
|
|
283
|
+
});
|
|
284
|
+
if (Array.isArray(result))
|
|
285
|
+
return result;
|
|
286
|
+
return result.artifacts || [];
|
|
287
|
+
}
|
|
288
|
+
/** Delete an artifact */
|
|
289
|
+
async delete(artifactId, conversationId) {
|
|
290
|
+
return this.client.request({
|
|
291
|
+
endpoint: `/api/agent/artifacts/${artifactId}?conversation_id=${conversationId}`,
|
|
292
|
+
method: 'DELETE',
|
|
293
|
+
useGateway: true,
|
|
294
|
+
});
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
// ============================================================================
|
|
298
|
+
// Results Sub-namespace
|
|
299
|
+
// ============================================================================
|
|
300
|
+
export class ResultsSubNamespace {
|
|
301
|
+
client;
|
|
302
|
+
constructor(client) {
|
|
303
|
+
this.client = client;
|
|
304
|
+
}
|
|
305
|
+
/** Get async result by key */
|
|
306
|
+
async get(resultKey) {
|
|
307
|
+
return this.client.request({
|
|
308
|
+
endpoint: `/api/results/${resultKey}`,
|
|
309
|
+
method: 'GET',
|
|
310
|
+
useGateway: true,
|
|
311
|
+
});
|
|
312
|
+
}
|
|
313
|
+
/** Poll for result until completion or timeout */
|
|
314
|
+
async poll(resultKey, options) {
|
|
315
|
+
const interval = options?.interval ?? 1000;
|
|
316
|
+
const timeout = options?.timeout ?? 300000;
|
|
317
|
+
const start = Date.now();
|
|
318
|
+
while (Date.now() - start < timeout) {
|
|
319
|
+
const result = await this.get(resultKey);
|
|
320
|
+
if (result.status === 'completed') {
|
|
321
|
+
return result;
|
|
322
|
+
}
|
|
323
|
+
if (result.status === 'failed') {
|
|
324
|
+
throw new Error(`Operation failed: ${result.error || 'Unknown error'}`);
|
|
325
|
+
}
|
|
326
|
+
await new Promise((resolve) => setTimeout(resolve, interval));
|
|
327
|
+
}
|
|
328
|
+
throw new Error(`Result polling timed out after ${timeout}ms`);
|
|
329
|
+
}
|
|
330
|
+
}
|
|
331
|
+
// ============================================================================
|
|
332
|
+
// Workflow Sub-namespace
|
|
333
|
+
// ============================================================================
|
|
334
|
+
export class WorkflowSubNamespace {
|
|
335
|
+
client;
|
|
336
|
+
constructor(client) {
|
|
337
|
+
this.client = client;
|
|
338
|
+
}
|
|
339
|
+
/** Execute a multi-agent workflow */
|
|
340
|
+
async execute(options) {
|
|
341
|
+
const body = {
|
|
342
|
+
workflow_id: options.workflowId,
|
|
343
|
+
input: options.input,
|
|
344
|
+
mode: options.mode || 'blocking',
|
|
345
|
+
};
|
|
346
|
+
if (options.conversationId)
|
|
347
|
+
body.conversation_id = options.conversationId;
|
|
348
|
+
if (options.webhookUrl)
|
|
349
|
+
body.webhook_url = options.webhookUrl;
|
|
350
|
+
return this.client.request({
|
|
351
|
+
endpoint: '/api/orchestration/execute',
|
|
352
|
+
body,
|
|
353
|
+
useGateway: true,
|
|
354
|
+
});
|
|
355
|
+
}
|
|
356
|
+
/** Validate a workflow definition */
|
|
357
|
+
async validate(workflowDefinition) {
|
|
358
|
+
return this.client.request({
|
|
359
|
+
endpoint: '/api/orchestration/validate',
|
|
360
|
+
body: { definition: workflowDefinition },
|
|
361
|
+
useGateway: true,
|
|
362
|
+
});
|
|
363
|
+
}
|
|
364
|
+
/** Get messages from an execution */
|
|
365
|
+
async messages(executionId, options) {
|
|
366
|
+
const result = await this.client.request({
|
|
367
|
+
endpoint: `/api/orchestration/messages/${executionId}`,
|
|
368
|
+
body: { limit: options?.limit ?? 100, offset: options?.offset ?? 0 },
|
|
369
|
+
useGateway: true,
|
|
370
|
+
});
|
|
371
|
+
if (Array.isArray(result))
|
|
372
|
+
return result;
|
|
373
|
+
return result.messages || [];
|
|
374
|
+
}
|
|
375
|
+
/** Replay events from an execution */
|
|
376
|
+
async events(executionId, fromTimestamp) {
|
|
377
|
+
const body = {};
|
|
378
|
+
if (fromTimestamp)
|
|
379
|
+
body.from = fromTimestamp;
|
|
380
|
+
const result = await this.client.request({
|
|
381
|
+
endpoint: `/api/orchestration/events/${executionId}`,
|
|
382
|
+
body: Object.keys(body).length > 0 ? body : undefined,
|
|
383
|
+
useGateway: true,
|
|
384
|
+
});
|
|
385
|
+
if (Array.isArray(result))
|
|
386
|
+
return result;
|
|
387
|
+
return result.events || [];
|
|
388
|
+
}
|
|
389
|
+
/** Get execution status */
|
|
390
|
+
async status(executionId) {
|
|
391
|
+
return this.client.request({
|
|
392
|
+
endpoint: `/api/orchestration/status/${executionId}`,
|
|
393
|
+
method: 'GET',
|
|
394
|
+
useGateway: true,
|
|
395
|
+
});
|
|
396
|
+
}
|
|
397
|
+
/** Get final execution output */
|
|
398
|
+
async output(executionId) {
|
|
399
|
+
return this.client.request({
|
|
400
|
+
endpoint: `/api/orchestration/output/${executionId}`,
|
|
401
|
+
method: 'GET',
|
|
402
|
+
useGateway: true,
|
|
403
|
+
});
|
|
404
|
+
}
|
|
405
|
+
}
|
|
406
|
+
// ============================================================================
|
|
407
|
+
// Main AI Namespace
|
|
408
|
+
// ============================================================================
|
|
409
|
+
export class AiNamespace {
|
|
410
|
+
client;
|
|
411
|
+
/** RAG corpus management */
|
|
412
|
+
rag;
|
|
413
|
+
/** Conversation artifacts */
|
|
414
|
+
artifacts;
|
|
415
|
+
/** Async result polling */
|
|
416
|
+
results;
|
|
417
|
+
/** Multi-agent workflow orchestration */
|
|
418
|
+
workflow;
|
|
419
|
+
constructor(client) {
|
|
420
|
+
this.client = client;
|
|
421
|
+
this.rag = new RagSubNamespace(client);
|
|
422
|
+
this.artifacts = new ArtifactsSubNamespace(client);
|
|
423
|
+
this.results = new ResultsSubNamespace(client);
|
|
424
|
+
this.workflow = new WorkflowSubNamespace(client);
|
|
425
|
+
}
|
|
426
|
+
// ========================================
|
|
427
|
+
// Agent Execution
|
|
428
|
+
// ========================================
|
|
429
|
+
/** Execute agent with blocking wait */
|
|
430
|
+
async runAgent(options) {
|
|
431
|
+
const body = {
|
|
432
|
+
conversation_id: options.conversationId,
|
|
433
|
+
system_prompt: options.systemPrompt,
|
|
434
|
+
user_prompt: options.userPrompt,
|
|
435
|
+
history_source: options.historySource || 'conversation_id',
|
|
436
|
+
model: options.model || 'claude-sonnet-4-5',
|
|
437
|
+
};
|
|
438
|
+
if (options.inlineHistory)
|
|
439
|
+
body.inline_history = options.inlineHistory;
|
|
440
|
+
if (options.preloadedContext)
|
|
441
|
+
body.preloaded_context = options.preloadedContext;
|
|
442
|
+
if (options.artifactRefs)
|
|
443
|
+
body.artifact_refs = options.artifactRefs;
|
|
444
|
+
if (options.toolAllowlist)
|
|
445
|
+
body.tool_allowlist = options.toolAllowlist;
|
|
446
|
+
if (options.guardrails)
|
|
447
|
+
body.guardrails = options.guardrails;
|
|
448
|
+
if (options.outputSchema)
|
|
449
|
+
body.output_schema = options.outputSchema;
|
|
450
|
+
if (options.toolEndpoint)
|
|
451
|
+
body.tool_endpoint = options.toolEndpoint;
|
|
452
|
+
const result = await this.client.request({
|
|
453
|
+
endpoint: '/api/agent/run',
|
|
454
|
+
body,
|
|
455
|
+
timeout: options.timeout,
|
|
456
|
+
useGateway: true,
|
|
457
|
+
});
|
|
458
|
+
// Normalize snake_case keys to camelCase
|
|
459
|
+
return normalizeResponse(result);
|
|
460
|
+
}
|
|
461
|
+
/** Execute agent with SSE streaming */
|
|
462
|
+
async *streamAgent(options) {
|
|
463
|
+
const body = {
|
|
464
|
+
conversation_id: options.conversationId,
|
|
465
|
+
system_prompt: options.systemPrompt,
|
|
466
|
+
user_prompt: options.userPrompt,
|
|
467
|
+
history_source: options.historySource || 'conversation_id',
|
|
468
|
+
model: options.model || 'claude-sonnet-4-5',
|
|
469
|
+
};
|
|
470
|
+
if (options.inlineHistory)
|
|
471
|
+
body.inline_history = options.inlineHistory;
|
|
472
|
+
if (options.preloadedContext)
|
|
473
|
+
body.preloaded_context = options.preloadedContext;
|
|
474
|
+
if (options.artifactRefs)
|
|
475
|
+
body.artifact_refs = options.artifactRefs;
|
|
476
|
+
if (options.toolAllowlist)
|
|
477
|
+
body.tool_allowlist = options.toolAllowlist;
|
|
478
|
+
if (options.guardrails)
|
|
479
|
+
body.guardrails = options.guardrails;
|
|
480
|
+
if (options.outputSchema)
|
|
481
|
+
body.output_schema = options.outputSchema;
|
|
482
|
+
if (options.toolEndpoint)
|
|
483
|
+
body.tool_endpoint = options.toolEndpoint;
|
|
484
|
+
for await (const chunk of this.client.streamRequest({
|
|
485
|
+
endpoint: '/api/agent/stream',
|
|
486
|
+
body,
|
|
487
|
+
onChunk: options.onChunk,
|
|
488
|
+
timeout: options.timeout || 300000,
|
|
489
|
+
useGateway: true,
|
|
490
|
+
})) {
|
|
491
|
+
// Normalize chunk and yield
|
|
492
|
+
const normalized = normalizeResponse(chunk);
|
|
493
|
+
yield normalized;
|
|
494
|
+
}
|
|
495
|
+
}
|
|
496
|
+
/** Fire-and-forget async execution */
|
|
497
|
+
async runAgentAsync(options) {
|
|
498
|
+
const body = {
|
|
499
|
+
conversation_id: options.conversationId,
|
|
500
|
+
system_prompt: options.systemPrompt,
|
|
501
|
+
user_prompt: options.userPrompt,
|
|
502
|
+
result_key: options.resultKey,
|
|
503
|
+
history_source: options.historySource || 'conversation_id',
|
|
504
|
+
model: options.model || 'claude-sonnet-4-5',
|
|
505
|
+
};
|
|
506
|
+
if (options.inlineHistory)
|
|
507
|
+
body.inline_history = options.inlineHistory;
|
|
508
|
+
if (options.preloadedContext)
|
|
509
|
+
body.preloaded_context = options.preloadedContext;
|
|
510
|
+
if (options.artifactRefs)
|
|
511
|
+
body.artifact_refs = options.artifactRefs;
|
|
512
|
+
if (options.toolAllowlist)
|
|
513
|
+
body.tool_allowlist = options.toolAllowlist;
|
|
514
|
+
if (options.guardrails)
|
|
515
|
+
body.guardrails = options.guardrails;
|
|
516
|
+
if (options.outputSchema)
|
|
517
|
+
body.output_schema = options.outputSchema;
|
|
518
|
+
if (options.toolEndpoint)
|
|
519
|
+
body.tool_endpoint = options.toolEndpoint;
|
|
520
|
+
if (options.webhookUrl)
|
|
521
|
+
body.webhook_url = options.webhookUrl;
|
|
522
|
+
return this.client.request({
|
|
523
|
+
endpoint: '/api/agent/run-async',
|
|
524
|
+
body,
|
|
525
|
+
useGateway: true,
|
|
526
|
+
});
|
|
527
|
+
}
|
|
528
|
+
// ========================================
|
|
529
|
+
// Conversation History
|
|
530
|
+
// ========================================
|
|
531
|
+
/** Get conversation history */
|
|
532
|
+
async history(conversationId, limit = 50) {
|
|
533
|
+
const result = await this.client.request({
|
|
534
|
+
endpoint: `/api/agent/history/${conversationId}?limit=${limit}`,
|
|
535
|
+
method: 'GET',
|
|
536
|
+
useGateway: true,
|
|
537
|
+
});
|
|
538
|
+
if (Array.isArray(result))
|
|
539
|
+
return result;
|
|
540
|
+
return result.messages || [];
|
|
541
|
+
}
|
|
542
|
+
// ========================================
|
|
543
|
+
// LLM Completions
|
|
544
|
+
// ========================================
|
|
545
|
+
/** Blocking LLM completion */
|
|
546
|
+
async complete(options) {
|
|
547
|
+
let systemPrompt = options.systemPrompt;
|
|
548
|
+
let userPrompt = options.userPrompt;
|
|
549
|
+
// Convert messages to system_prompt/user_prompt if needed
|
|
550
|
+
if (options.messages && !userPrompt) {
|
|
551
|
+
for (const msg of options.messages) {
|
|
552
|
+
if (msg.role === 'system') {
|
|
553
|
+
systemPrompt = msg.content;
|
|
554
|
+
}
|
|
555
|
+
else if (msg.role === 'user') {
|
|
556
|
+
userPrompt = msg.content;
|
|
557
|
+
}
|
|
558
|
+
}
|
|
559
|
+
}
|
|
560
|
+
if (!systemPrompt) {
|
|
561
|
+
systemPrompt = 'You are a helpful assistant.';
|
|
562
|
+
}
|
|
563
|
+
if (!userPrompt) {
|
|
564
|
+
throw new Error("Either 'messages' with a user message or 'userPrompt' is required");
|
|
565
|
+
}
|
|
566
|
+
const body = {
|
|
567
|
+
provider: options.provider || 'claude',
|
|
568
|
+
model: options.model || 'claude-sonnet-4-5',
|
|
569
|
+
system_prompt: systemPrompt,
|
|
570
|
+
user_prompt: userPrompt,
|
|
571
|
+
temperature: options.temperature ?? 0.7,
|
|
572
|
+
};
|
|
573
|
+
if (options.conversationId)
|
|
574
|
+
body.conversation_id = options.conversationId;
|
|
575
|
+
if (options.maxTokens)
|
|
576
|
+
body.max_tokens = options.maxTokens;
|
|
577
|
+
return this.client.request({
|
|
578
|
+
endpoint: '/api/llm/complete',
|
|
579
|
+
body,
|
|
580
|
+
timeout: options.timeout,
|
|
581
|
+
useGateway: true,
|
|
582
|
+
});
|
|
583
|
+
}
|
|
584
|
+
/** Streaming LLM completion */
|
|
585
|
+
async *completeStream(options) {
|
|
586
|
+
let systemPrompt = options.systemPrompt;
|
|
587
|
+
let userPrompt = options.userPrompt;
|
|
588
|
+
// Convert messages to system_prompt/user_prompt if needed
|
|
589
|
+
if (options.messages && !userPrompt) {
|
|
590
|
+
for (const msg of options.messages) {
|
|
591
|
+
if (msg.role === 'system') {
|
|
592
|
+
systemPrompt = msg.content;
|
|
593
|
+
}
|
|
594
|
+
else if (msg.role === 'user') {
|
|
595
|
+
userPrompt = msg.content;
|
|
596
|
+
}
|
|
597
|
+
}
|
|
598
|
+
}
|
|
599
|
+
if (!systemPrompt) {
|
|
600
|
+
systemPrompt = 'You are a helpful assistant.';
|
|
601
|
+
}
|
|
602
|
+
if (!userPrompt) {
|
|
603
|
+
throw new Error("Either 'messages' with a user message or 'userPrompt' is required");
|
|
604
|
+
}
|
|
605
|
+
const body = {
|
|
606
|
+
provider: options.provider || 'claude',
|
|
607
|
+
model: options.model || 'claude-sonnet-4-5',
|
|
608
|
+
system_prompt: systemPrompt,
|
|
609
|
+
user_prompt: userPrompt,
|
|
610
|
+
temperature: options.temperature ?? 0.7,
|
|
611
|
+
};
|
|
612
|
+
if (options.conversationId)
|
|
613
|
+
body.conversation_id = options.conversationId;
|
|
614
|
+
if (options.maxTokens)
|
|
615
|
+
body.max_tokens = options.maxTokens;
|
|
616
|
+
for await (const chunk of this.client.streamRequest({
|
|
617
|
+
endpoint: '/api/llm/stream',
|
|
618
|
+
body,
|
|
619
|
+
onChunk: options.onChunk,
|
|
620
|
+
timeout: options.timeout || 120000,
|
|
621
|
+
useGateway: true,
|
|
622
|
+
})) {
|
|
623
|
+
// Normalize chunk and yield
|
|
624
|
+
const normalized = normalizeResponse(chunk);
|
|
625
|
+
yield normalized;
|
|
626
|
+
}
|
|
627
|
+
}
|
|
628
|
+
// ========================================
|
|
629
|
+
// Speech Services
|
|
630
|
+
// ========================================
|
|
631
|
+
/** Speech-to-text conversion */
|
|
632
|
+
async stt(audio, options) {
|
|
633
|
+
const format = options?.format || 'wav';
|
|
634
|
+
const additionalFields = {};
|
|
635
|
+
if (options?.language)
|
|
636
|
+
additionalFields.language = options.language;
|
|
637
|
+
const result = await this.client.binaryUpload({
|
|
638
|
+
endpoint: '/api/agent/stt',
|
|
639
|
+
fileBytes: audio,
|
|
640
|
+
filename: `audio.${format}`,
|
|
641
|
+
contentType: `audio/${format}`,
|
|
642
|
+
additionalFields: Object.keys(additionalFields).length > 0 ? additionalFields : undefined,
|
|
643
|
+
useGateway: true,
|
|
644
|
+
});
|
|
645
|
+
return result;
|
|
646
|
+
}
|
|
647
|
+
/** Text-to-speech conversion */
|
|
648
|
+
async tts(text, options) {
|
|
649
|
+
return this.client.binaryDownload({
|
|
650
|
+
endpoint: '/api/agent/tts',
|
|
651
|
+
body: {
|
|
652
|
+
text,
|
|
653
|
+
voice: options?.voice || 'nova',
|
|
654
|
+
format: options?.format || 'mp3',
|
|
655
|
+
speed: options?.speed ?? 1.0,
|
|
656
|
+
},
|
|
657
|
+
useGateway: true,
|
|
658
|
+
});
|
|
659
|
+
}
|
|
660
|
+
// ========================================
|
|
661
|
+
// Pre-flight Setup
|
|
662
|
+
// ========================================
|
|
663
|
+
/** Pre-flight session setup */
|
|
664
|
+
async setup(options) {
|
|
665
|
+
const body = {
|
|
666
|
+
conversation_id: options.conversationId,
|
|
667
|
+
};
|
|
668
|
+
if (options.artifacts)
|
|
669
|
+
body.artifacts = options.artifacts;
|
|
670
|
+
if (options.ragCorpus)
|
|
671
|
+
body.rag_corpus = options.ragCorpus;
|
|
672
|
+
if (options.context)
|
|
673
|
+
body.context = options.context;
|
|
674
|
+
const result = await this.client.request({
|
|
675
|
+
endpoint: '/api/session/setup',
|
|
676
|
+
body,
|
|
677
|
+
useGateway: true,
|
|
678
|
+
});
|
|
679
|
+
// Normalize snake_case keys to camelCase
|
|
680
|
+
return normalizeResponse(result);
|
|
681
|
+
}
|
|
682
|
+
}
|
|
683
|
+
//# sourceMappingURL=ai.js.map
|