@octavus/server-sdk 2.2.0 → 2.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +99 -1
- package/dist/index.js +297 -164
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.d.ts
CHANGED
|
@@ -346,6 +346,103 @@ declare class FilesApi extends BaseApiClient {
|
|
|
346
346
|
getUploadUrls(sessionId: string, files: FileUploadRequest[]): Promise<UploadUrlsResponse>;
|
|
347
347
|
}
|
|
348
348
|
|
|
349
|
+
/** Start a new worker execution */
|
|
350
|
+
interface WorkerStartRequest {
|
|
351
|
+
type: 'start';
|
|
352
|
+
input: Record<string, unknown>;
|
|
353
|
+
}
|
|
354
|
+
/** Continue execution after client-side tool handling */
|
|
355
|
+
interface WorkerContinueRequest {
|
|
356
|
+
type: 'continue';
|
|
357
|
+
executionId: string;
|
|
358
|
+
toolResults: ToolResult[];
|
|
359
|
+
}
|
|
360
|
+
/** All request types supported by workers */
|
|
361
|
+
type WorkerRequest = WorkerStartRequest | WorkerContinueRequest;
|
|
362
|
+
/** Options for worker execution */
|
|
363
|
+
interface WorkerExecuteOptions {
|
|
364
|
+
/** Tool handlers for server-side tool execution */
|
|
365
|
+
tools?: ToolHandlers;
|
|
366
|
+
/** Abort signal to cancel the execution */
|
|
367
|
+
signal?: AbortSignal;
|
|
368
|
+
}
|
|
369
|
+
/** API for executing worker agents */
|
|
370
|
+
declare class WorkersApi extends BaseApiClient {
|
|
371
|
+
/**
|
|
372
|
+
* Execute a worker agent and stream the response.
|
|
373
|
+
*
|
|
374
|
+
* Worker agents execute steps sequentially and return an output value.
|
|
375
|
+
* Unlike interactive sessions, workers don't maintain persistent state.
|
|
376
|
+
*
|
|
377
|
+
* The execution handles the tool continuation pattern automatically:
|
|
378
|
+
* - Server tools (with handlers provided) are executed automatically
|
|
379
|
+
* - Client tools (without handlers) emit a client-tool-request event
|
|
380
|
+
*
|
|
381
|
+
* @param agentId - The worker agent ID
|
|
382
|
+
* @param input - Input values for the worker
|
|
383
|
+
* @param options - Optional configuration including tools and abort signal
|
|
384
|
+
* @returns An async generator of stream events
|
|
385
|
+
*
|
|
386
|
+
* @example Basic execution
|
|
387
|
+
* ```typescript
|
|
388
|
+
* const events = client.workers.execute(agentId, { TOPIC: 'AI safety' });
|
|
389
|
+
* for await (const event of events) {
|
|
390
|
+
* if (event.type === 'worker-start') {
|
|
391
|
+
* console.log(`Worker ${event.workerSlug} started (${event.workerId})`);
|
|
392
|
+
* }
|
|
393
|
+
* if (event.type === 'worker-result') {
|
|
394
|
+
* if (event.error) {
|
|
395
|
+
* console.error('Worker failed:', event.error);
|
|
396
|
+
* } else {
|
|
397
|
+
* console.log('Output:', event.output);
|
|
398
|
+
* }
|
|
399
|
+
* }
|
|
400
|
+
* }
|
|
401
|
+
* ```
|
|
402
|
+
*
|
|
403
|
+
* @example With tool handlers
|
|
404
|
+
* ```typescript
|
|
405
|
+
* const events = client.workers.execute(agentId, { TOPIC: 'AI safety' }, {
|
|
406
|
+
* tools: {
|
|
407
|
+
* 'web-search': async (args) => {
|
|
408
|
+
* return await searchWeb(args.query);
|
|
409
|
+
* },
|
|
410
|
+
* },
|
|
411
|
+
* });
|
|
412
|
+
* ```
|
|
413
|
+
*/
|
|
414
|
+
execute(agentId: string, input: Record<string, unknown>, options?: WorkerExecuteOptions): AsyncGenerator<StreamEvent>;
|
|
415
|
+
/**
|
|
416
|
+
* Continue a worker execution after client-side tool handling.
|
|
417
|
+
*
|
|
418
|
+
* Use this when your worker has tools without server-side handlers.
|
|
419
|
+
* The execution returns a client-tool-request event with an executionId.
|
|
420
|
+
* Execute the tools client-side, then call this method to continue.
|
|
421
|
+
*
|
|
422
|
+
* @param agentId - The worker agent ID
|
|
423
|
+
* @param executionId - The execution ID from the client-tool-request event
|
|
424
|
+
* @param toolResults - Results from client-side tool execution
|
|
425
|
+
* @param options - Optional configuration including tools and abort signal
|
|
426
|
+
* @returns An async generator of stream events
|
|
427
|
+
*
|
|
428
|
+
* @example
|
|
429
|
+
* ```typescript
|
|
430
|
+
* // Start execution
|
|
431
|
+
* for await (const event of client.workers.execute(agentId, input)) {
|
|
432
|
+
* if (event.type === 'client-tool-request') {
|
|
433
|
+
* // Execute tools client-side
|
|
434
|
+
* const results = await executeToolsClientSide(event.toolCalls);
|
|
435
|
+
* // Continue execution
|
|
436
|
+
* for await (const ev of client.workers.continue(agentId, event.executionId, results)) {
|
|
437
|
+
* // Handle remaining events
|
|
438
|
+
* }
|
|
439
|
+
* }
|
|
440
|
+
* }
|
|
441
|
+
* ```
|
|
442
|
+
*/
|
|
443
|
+
continue(agentId: string, executionId: string, toolResults: ToolResult[], options?: WorkerExecuteOptions): AsyncGenerator<StreamEvent>;
|
|
444
|
+
}
|
|
445
|
+
|
|
349
446
|
interface OctavusClientConfig {
|
|
350
447
|
baseUrl: string;
|
|
351
448
|
apiKey?: string;
|
|
@@ -355,10 +452,11 @@ declare class OctavusClient {
|
|
|
355
452
|
readonly agents: AgentsApi;
|
|
356
453
|
readonly agentSessions: AgentSessionsApi;
|
|
357
454
|
readonly files: FilesApi;
|
|
455
|
+
readonly workers: WorkersApi;
|
|
358
456
|
readonly baseUrl: string;
|
|
359
457
|
private readonly apiKey?;
|
|
360
458
|
constructor(config: OctavusClientConfig);
|
|
361
459
|
getHeaders(): Record<string, string>;
|
|
362
460
|
}
|
|
363
461
|
|
|
364
|
-
export { type Agent, type AgentDefinition, type AgentFormat, type AgentPrompt, AgentSession, AgentSessionsApi, type AgentSettings, AgentsApi, ApiError, type ContinueRequest, type ExpiredSessionState, type FileUploadInfo, type FileUploadRequest, FilesApi, OctavusClient, type OctavusClientConfig, Resource, type RestoreSessionResult, type SessionAttachOptions, type SessionConfig, type SessionRequest, type SessionState, type SessionStatus, type SocketMessage, type SocketMessageHandlers, type StopMessage, type TriggerOptions, type TriggerRequest, type UISessionState, type UploadUrlsResponse, toSSEStream };
|
|
462
|
+
export { type Agent, type AgentDefinition, type AgentFormat, type AgentPrompt, AgentSession, AgentSessionsApi, type AgentSettings, AgentsApi, ApiError, type ContinueRequest, type ExpiredSessionState, type FileUploadInfo, type FileUploadRequest, FilesApi, OctavusClient, type OctavusClientConfig, Resource, type RestoreSessionResult, type SessionAttachOptions, type SessionConfig, type SessionRequest, type SessionState, type SessionStatus, type SocketMessage, type SocketMessageHandlers, type StopMessage, type TriggerOptions, type TriggerRequest, type UISessionState, type UploadUrlsResponse, type WorkerContinueRequest, type WorkerExecuteOptions, type WorkerRequest, type WorkerStartRequest, WorkersApi, toSSEStream };
|
package/dist/index.js
CHANGED
|
@@ -130,12 +130,178 @@ import {
|
|
|
130
130
|
} from "@octavus/core";
|
|
131
131
|
|
|
132
132
|
// src/session.ts
|
|
133
|
+
import {
|
|
134
|
+
createInternalErrorEvent as createInternalErrorEvent2
|
|
135
|
+
} from "@octavus/core";
|
|
136
|
+
|
|
137
|
+
// src/streaming.ts
|
|
133
138
|
import {
|
|
134
139
|
safeParseStreamEvent,
|
|
135
140
|
isAbortError,
|
|
136
141
|
createInternalErrorEvent,
|
|
137
142
|
createApiErrorEvent
|
|
138
143
|
} from "@octavus/core";
|
|
144
|
+
async function* executeStream(config, payload, signal) {
|
|
145
|
+
let toolResults = payload.toolResults;
|
|
146
|
+
let executionId = payload.executionId;
|
|
147
|
+
let continueLoop = true;
|
|
148
|
+
while (continueLoop) {
|
|
149
|
+
if (signal?.aborted) {
|
|
150
|
+
yield { type: "finish", finishReason: "stop" };
|
|
151
|
+
return;
|
|
152
|
+
}
|
|
153
|
+
const body = config.buildBody({ executionId, toolResults });
|
|
154
|
+
let response;
|
|
155
|
+
try {
|
|
156
|
+
response = await fetch(config.url, {
|
|
157
|
+
method: "POST",
|
|
158
|
+
headers: config.config.getHeaders(),
|
|
159
|
+
body: JSON.stringify(body),
|
|
160
|
+
signal
|
|
161
|
+
});
|
|
162
|
+
} catch (err) {
|
|
163
|
+
if (isAbortError(err)) {
|
|
164
|
+
yield { type: "finish", finishReason: "stop" };
|
|
165
|
+
return;
|
|
166
|
+
}
|
|
167
|
+
throw err;
|
|
168
|
+
}
|
|
169
|
+
if (!response.ok) {
|
|
170
|
+
const { message } = await parseApiError(response, config.errorContext ?? "Request failed");
|
|
171
|
+
yield createApiErrorEvent(response.status, message);
|
|
172
|
+
return;
|
|
173
|
+
}
|
|
174
|
+
if (!response.body) {
|
|
175
|
+
yield createInternalErrorEvent("Response body is not readable");
|
|
176
|
+
return;
|
|
177
|
+
}
|
|
178
|
+
toolResults = void 0;
|
|
179
|
+
const reader = response.body.getReader();
|
|
180
|
+
const decoder = new TextDecoder();
|
|
181
|
+
let buffer = "";
|
|
182
|
+
let pendingToolCalls = null;
|
|
183
|
+
let streamDone = false;
|
|
184
|
+
while (!streamDone) {
|
|
185
|
+
if (signal?.aborted) {
|
|
186
|
+
reader.releaseLock();
|
|
187
|
+
yield { type: "finish", finishReason: "stop" };
|
|
188
|
+
return;
|
|
189
|
+
}
|
|
190
|
+
let readResult;
|
|
191
|
+
try {
|
|
192
|
+
readResult = await reader.read();
|
|
193
|
+
} catch (err) {
|
|
194
|
+
if (isAbortError(err)) {
|
|
195
|
+
reader.releaseLock();
|
|
196
|
+
yield { type: "finish", finishReason: "stop" };
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
throw err;
|
|
200
|
+
}
|
|
201
|
+
const { done, value } = readResult;
|
|
202
|
+
if (done) {
|
|
203
|
+
streamDone = true;
|
|
204
|
+
continue;
|
|
205
|
+
}
|
|
206
|
+
buffer += decoder.decode(value, { stream: true });
|
|
207
|
+
const lines = buffer.split("\n");
|
|
208
|
+
buffer = lines.pop() ?? "";
|
|
209
|
+
for (const line of lines) {
|
|
210
|
+
if (line.startsWith("data: ") && line !== "data: [DONE]") {
|
|
211
|
+
try {
|
|
212
|
+
const parsed = safeParseStreamEvent(JSON.parse(line.slice(6)));
|
|
213
|
+
if (!parsed.success) {
|
|
214
|
+
continue;
|
|
215
|
+
}
|
|
216
|
+
const event = parsed.data;
|
|
217
|
+
if (event.type === "start" && event.executionId) {
|
|
218
|
+
executionId = event.executionId;
|
|
219
|
+
}
|
|
220
|
+
if (event.type === "tool-request") {
|
|
221
|
+
pendingToolCalls = event.toolCalls;
|
|
222
|
+
continue;
|
|
223
|
+
}
|
|
224
|
+
if (event.type === "finish") {
|
|
225
|
+
if (event.finishReason === "tool-calls" && pendingToolCalls) {
|
|
226
|
+
continue;
|
|
227
|
+
}
|
|
228
|
+
yield event;
|
|
229
|
+
continueLoop = false;
|
|
230
|
+
continue;
|
|
231
|
+
}
|
|
232
|
+
if (event.type === "resource-update" && config.onResourceUpdate) {
|
|
233
|
+
config.onResourceUpdate(event.name, event.value);
|
|
234
|
+
}
|
|
235
|
+
yield event;
|
|
236
|
+
} catch {
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
if (signal?.aborted) {
|
|
242
|
+
yield { type: "finish", finishReason: "stop" };
|
|
243
|
+
return;
|
|
244
|
+
}
|
|
245
|
+
if (pendingToolCalls && pendingToolCalls.length > 0) {
|
|
246
|
+
const serverTools = pendingToolCalls.filter((tc) => config.toolHandlers[tc.toolName]);
|
|
247
|
+
const clientTools = pendingToolCalls.filter((tc) => !config.toolHandlers[tc.toolName]);
|
|
248
|
+
const serverResults = await Promise.all(
|
|
249
|
+
serverTools.map(async (tc) => {
|
|
250
|
+
const handler = config.toolHandlers[tc.toolName];
|
|
251
|
+
try {
|
|
252
|
+
const result = await handler(tc.args);
|
|
253
|
+
return {
|
|
254
|
+
toolCallId: tc.toolCallId,
|
|
255
|
+
toolName: tc.toolName,
|
|
256
|
+
result,
|
|
257
|
+
outputVariable: tc.outputVariable,
|
|
258
|
+
blockIndex: tc.blockIndex,
|
|
259
|
+
thread: tc.thread,
|
|
260
|
+
workerId: tc.workerId
|
|
261
|
+
};
|
|
262
|
+
} catch (err) {
|
|
263
|
+
return {
|
|
264
|
+
toolCallId: tc.toolCallId,
|
|
265
|
+
toolName: tc.toolName,
|
|
266
|
+
error: err instanceof Error ? err.message : "Tool execution failed",
|
|
267
|
+
outputVariable: tc.outputVariable,
|
|
268
|
+
blockIndex: tc.blockIndex,
|
|
269
|
+
thread: tc.thread,
|
|
270
|
+
workerId: tc.workerId
|
|
271
|
+
};
|
|
272
|
+
}
|
|
273
|
+
})
|
|
274
|
+
);
|
|
275
|
+
for (const tr of serverResults) {
|
|
276
|
+
if (tr.error) {
|
|
277
|
+
yield { type: "tool-output-error", toolCallId: tr.toolCallId, error: tr.error };
|
|
278
|
+
} else {
|
|
279
|
+
yield { type: "tool-output-available", toolCallId: tr.toolCallId, output: tr.result };
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
if (clientTools.length > 0) {
|
|
283
|
+
if (!executionId) {
|
|
284
|
+
yield createInternalErrorEvent("Missing executionId for client-tool-request");
|
|
285
|
+
return;
|
|
286
|
+
}
|
|
287
|
+
yield {
|
|
288
|
+
type: "client-tool-request",
|
|
289
|
+
executionId,
|
|
290
|
+
toolCalls: clientTools,
|
|
291
|
+
serverToolResults: serverResults.length > 0 ? serverResults : void 0
|
|
292
|
+
};
|
|
293
|
+
yield { type: "finish", finishReason: "client-tool-calls", executionId };
|
|
294
|
+
continueLoop = false;
|
|
295
|
+
} else {
|
|
296
|
+
toolResults = serverResults;
|
|
297
|
+
}
|
|
298
|
+
} else {
|
|
299
|
+
continueLoop = false;
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
}
|
|
303
|
+
|
|
304
|
+
// src/session.ts
|
|
139
305
|
function toSSEStream(events) {
|
|
140
306
|
const encoder = new TextEncoder();
|
|
141
307
|
return new ReadableStream({
|
|
@@ -149,7 +315,7 @@ function toSSEStream(events) {
|
|
|
149
315
|
controller.enqueue(encoder.encode("data: [DONE]\n\n"));
|
|
150
316
|
controller.close();
|
|
151
317
|
} catch (err) {
|
|
152
|
-
const errorEvent =
|
|
318
|
+
const errorEvent = createInternalErrorEvent2(
|
|
153
319
|
err instanceof Error ? err.message : "Unknown error"
|
|
154
320
|
);
|
|
155
321
|
controller.enqueue(encoder.encode(`data: ${JSON.stringify(errorEvent)}
|
|
@@ -249,7 +415,7 @@ var AgentSession = class {
|
|
|
249
415
|
}
|
|
250
416
|
} catch (err) {
|
|
251
417
|
if (!localController.signal.aborted) {
|
|
252
|
-
const errorEvent =
|
|
418
|
+
const errorEvent = createInternalErrorEvent2(
|
|
253
419
|
err instanceof Error ? err.message : "Unknown error"
|
|
254
420
|
);
|
|
255
421
|
handlers.onEvent(errorEvent);
|
|
@@ -257,166 +423,25 @@ var AgentSession = class {
|
|
|
257
423
|
}
|
|
258
424
|
}
|
|
259
425
|
async *executeStream(payload, signal) {
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
headers: this.config.getHeaders(),
|
|
280
|
-
body: JSON.stringify(body),
|
|
281
|
-
signal
|
|
282
|
-
}
|
|
283
|
-
);
|
|
284
|
-
} catch (err) {
|
|
285
|
-
if (isAbortError(err)) {
|
|
286
|
-
yield { type: "finish", finishReason: "stop" };
|
|
287
|
-
return;
|
|
288
|
-
}
|
|
289
|
-
throw err;
|
|
290
|
-
}
|
|
291
|
-
if (!response.ok) {
|
|
292
|
-
const { message } = await parseApiError(response, "Failed to trigger");
|
|
293
|
-
yield createApiErrorEvent(response.status, message);
|
|
294
|
-
return;
|
|
295
|
-
}
|
|
296
|
-
if (!response.body) {
|
|
297
|
-
yield createInternalErrorEvent("Response body is not readable");
|
|
298
|
-
return;
|
|
299
|
-
}
|
|
300
|
-
toolResults = void 0;
|
|
301
|
-
const reader = response.body.getReader();
|
|
302
|
-
const decoder = new TextDecoder();
|
|
303
|
-
let buffer = "";
|
|
304
|
-
let pendingToolCalls = null;
|
|
305
|
-
let streamDone = false;
|
|
306
|
-
while (!streamDone) {
|
|
307
|
-
if (signal?.aborted) {
|
|
308
|
-
reader.releaseLock();
|
|
309
|
-
yield { type: "finish", finishReason: "stop" };
|
|
310
|
-
return;
|
|
311
|
-
}
|
|
312
|
-
let readResult;
|
|
313
|
-
try {
|
|
314
|
-
readResult = await reader.read();
|
|
315
|
-
} catch (err) {
|
|
316
|
-
if (isAbortError(err)) {
|
|
317
|
-
reader.releaseLock();
|
|
318
|
-
yield { type: "finish", finishReason: "stop" };
|
|
319
|
-
return;
|
|
320
|
-
}
|
|
321
|
-
throw err;
|
|
322
|
-
}
|
|
323
|
-
const { done, value } = readResult;
|
|
324
|
-
if (done) {
|
|
325
|
-
streamDone = true;
|
|
326
|
-
continue;
|
|
327
|
-
}
|
|
328
|
-
buffer += decoder.decode(value, { stream: true });
|
|
329
|
-
const lines = buffer.split("\n");
|
|
330
|
-
buffer = lines.pop() ?? "";
|
|
331
|
-
for (const line of lines) {
|
|
332
|
-
if (line.startsWith("data: ") && line !== "data: [DONE]") {
|
|
333
|
-
try {
|
|
334
|
-
const parsed = safeParseStreamEvent(JSON.parse(line.slice(6)));
|
|
335
|
-
if (!parsed.success) {
|
|
336
|
-
continue;
|
|
337
|
-
}
|
|
338
|
-
const event = parsed.data;
|
|
339
|
-
if (event.type === "start" && event.executionId) {
|
|
340
|
-
executionId = event.executionId;
|
|
341
|
-
}
|
|
342
|
-
if (event.type === "tool-request") {
|
|
343
|
-
pendingToolCalls = event.toolCalls;
|
|
344
|
-
continue;
|
|
345
|
-
}
|
|
346
|
-
if (event.type === "finish") {
|
|
347
|
-
if (event.finishReason === "tool-calls" && pendingToolCalls) {
|
|
348
|
-
continue;
|
|
349
|
-
}
|
|
350
|
-
yield event;
|
|
351
|
-
continueLoop = false;
|
|
352
|
-
continue;
|
|
353
|
-
}
|
|
354
|
-
if (event.type === "resource-update") {
|
|
355
|
-
this.handleResourceUpdate(event.name, event.value);
|
|
356
|
-
}
|
|
357
|
-
yield event;
|
|
358
|
-
} catch {
|
|
359
|
-
}
|
|
360
|
-
}
|
|
361
|
-
}
|
|
362
|
-
}
|
|
363
|
-
if (signal?.aborted) {
|
|
364
|
-
yield { type: "finish", finishReason: "stop" };
|
|
365
|
-
return;
|
|
366
|
-
}
|
|
367
|
-
if (pendingToolCalls && pendingToolCalls.length > 0) {
|
|
368
|
-
const serverTools = pendingToolCalls.filter((tc) => this.toolHandlers[tc.toolName]);
|
|
369
|
-
const clientTools = pendingToolCalls.filter((tc) => !this.toolHandlers[tc.toolName]);
|
|
370
|
-
const serverResults = await Promise.all(
|
|
371
|
-
serverTools.map(async (tc) => {
|
|
372
|
-
const handler = this.toolHandlers[tc.toolName];
|
|
373
|
-
try {
|
|
374
|
-
const result = await handler(tc.args);
|
|
375
|
-
return {
|
|
376
|
-
toolCallId: tc.toolCallId,
|
|
377
|
-
toolName: tc.toolName,
|
|
378
|
-
result,
|
|
379
|
-
outputVariable: tc.outputVariable,
|
|
380
|
-
blockIndex: tc.blockIndex
|
|
381
|
-
};
|
|
382
|
-
} catch (err) {
|
|
383
|
-
return {
|
|
384
|
-
toolCallId: tc.toolCallId,
|
|
385
|
-
toolName: tc.toolName,
|
|
386
|
-
error: err instanceof Error ? err.message : "Tool execution failed",
|
|
387
|
-
outputVariable: tc.outputVariable,
|
|
388
|
-
blockIndex: tc.blockIndex
|
|
389
|
-
};
|
|
390
|
-
}
|
|
391
|
-
})
|
|
392
|
-
);
|
|
393
|
-
for (const tr of serverResults) {
|
|
394
|
-
if (tr.error) {
|
|
395
|
-
yield { type: "tool-output-error", toolCallId: tr.toolCallId, error: tr.error };
|
|
396
|
-
} else {
|
|
397
|
-
yield { type: "tool-output-available", toolCallId: tr.toolCallId, output: tr.result };
|
|
398
|
-
}
|
|
399
|
-
}
|
|
400
|
-
if (clientTools.length > 0) {
|
|
401
|
-
if (!executionId) {
|
|
402
|
-
yield createInternalErrorEvent("Missing executionId for client-tool-request");
|
|
403
|
-
return;
|
|
404
|
-
}
|
|
405
|
-
yield {
|
|
406
|
-
type: "client-tool-request",
|
|
407
|
-
executionId,
|
|
408
|
-
toolCalls: clientTools,
|
|
409
|
-
serverToolResults: serverResults.length > 0 ? serverResults : void 0
|
|
410
|
-
};
|
|
411
|
-
yield { type: "finish", finishReason: "client-tool-calls", executionId };
|
|
412
|
-
continueLoop = false;
|
|
413
|
-
} else {
|
|
414
|
-
toolResults = serverResults;
|
|
415
|
-
}
|
|
416
|
-
} else {
|
|
417
|
-
continueLoop = false;
|
|
418
|
-
}
|
|
419
|
-
}
|
|
426
|
+
yield* executeStream(
|
|
427
|
+
{
|
|
428
|
+
config: this.config,
|
|
429
|
+
toolHandlers: this.toolHandlers,
|
|
430
|
+
url: `${this.config.baseUrl}/api/agent-sessions/${this.sessionId}/trigger`,
|
|
431
|
+
buildBody: ({ executionId, toolResults }) => {
|
|
432
|
+
const body = {};
|
|
433
|
+
if (payload.triggerName !== void 0) body.triggerName = payload.triggerName;
|
|
434
|
+
if (payload.input !== void 0) body.input = payload.input;
|
|
435
|
+
if (executionId !== void 0) body.executionId = executionId;
|
|
436
|
+
if (toolResults !== void 0) body.toolResults = toolResults;
|
|
437
|
+
return body;
|
|
438
|
+
},
|
|
439
|
+
onResourceUpdate: (name, value) => this.handleResourceUpdate(name, value),
|
|
440
|
+
errorContext: "Failed to trigger"
|
|
441
|
+
},
|
|
442
|
+
{ executionId: payload.executionId, toolResults: payload.toolResults },
|
|
443
|
+
signal
|
|
444
|
+
);
|
|
420
445
|
}
|
|
421
446
|
handleResourceUpdate(name, value) {
|
|
422
447
|
const resource = this.resourceMap.get(name);
|
|
@@ -595,11 +620,117 @@ var FilesApi = class extends BaseApiClient {
|
|
|
595
620
|
}
|
|
596
621
|
};
|
|
597
622
|
|
|
623
|
+
// src/workers.ts
|
|
624
|
+
var WorkersApi = class extends BaseApiClient {
|
|
625
|
+
/**
|
|
626
|
+
* Execute a worker agent and stream the response.
|
|
627
|
+
*
|
|
628
|
+
* Worker agents execute steps sequentially and return an output value.
|
|
629
|
+
* Unlike interactive sessions, workers don't maintain persistent state.
|
|
630
|
+
*
|
|
631
|
+
* The execution handles the tool continuation pattern automatically:
|
|
632
|
+
* - Server tools (with handlers provided) are executed automatically
|
|
633
|
+
* - Client tools (without handlers) emit a client-tool-request event
|
|
634
|
+
*
|
|
635
|
+
* @param agentId - The worker agent ID
|
|
636
|
+
* @param input - Input values for the worker
|
|
637
|
+
* @param options - Optional configuration including tools and abort signal
|
|
638
|
+
* @returns An async generator of stream events
|
|
639
|
+
*
|
|
640
|
+
* @example Basic execution
|
|
641
|
+
* ```typescript
|
|
642
|
+
* const events = client.workers.execute(agentId, { TOPIC: 'AI safety' });
|
|
643
|
+
* for await (const event of events) {
|
|
644
|
+
* if (event.type === 'worker-start') {
|
|
645
|
+
* console.log(`Worker ${event.workerSlug} started (${event.workerId})`);
|
|
646
|
+
* }
|
|
647
|
+
* if (event.type === 'worker-result') {
|
|
648
|
+
* if (event.error) {
|
|
649
|
+
* console.error('Worker failed:', event.error);
|
|
650
|
+
* } else {
|
|
651
|
+
* console.log('Output:', event.output);
|
|
652
|
+
* }
|
|
653
|
+
* }
|
|
654
|
+
* }
|
|
655
|
+
* ```
|
|
656
|
+
*
|
|
657
|
+
* @example With tool handlers
|
|
658
|
+
* ```typescript
|
|
659
|
+
* const events = client.workers.execute(agentId, { TOPIC: 'AI safety' }, {
|
|
660
|
+
* tools: {
|
|
661
|
+
* 'web-search': async (args) => {
|
|
662
|
+
* return await searchWeb(args.query);
|
|
663
|
+
* },
|
|
664
|
+
* },
|
|
665
|
+
* });
|
|
666
|
+
* ```
|
|
667
|
+
*/
|
|
668
|
+
async *execute(agentId, input, options = {}) {
|
|
669
|
+
yield* executeStream(
|
|
670
|
+
{
|
|
671
|
+
config: this.config,
|
|
672
|
+
toolHandlers: options.tools ?? {},
|
|
673
|
+
url: `${this.config.baseUrl}/api/agents/${agentId}/execute`,
|
|
674
|
+
buildBody: ({ executionId, toolResults }) => !executionId ? { type: "start", input } : { type: "continue", executionId, toolResults },
|
|
675
|
+
errorContext: "Failed to execute worker"
|
|
676
|
+
},
|
|
677
|
+
{},
|
|
678
|
+
options.signal
|
|
679
|
+
);
|
|
680
|
+
}
|
|
681
|
+
/**
|
|
682
|
+
* Continue a worker execution after client-side tool handling.
|
|
683
|
+
*
|
|
684
|
+
* Use this when your worker has tools without server-side handlers.
|
|
685
|
+
* The execution returns a client-tool-request event with an executionId.
|
|
686
|
+
* Execute the tools client-side, then call this method to continue.
|
|
687
|
+
*
|
|
688
|
+
* @param agentId - The worker agent ID
|
|
689
|
+
* @param executionId - The execution ID from the client-tool-request event
|
|
690
|
+
* @param toolResults - Results from client-side tool execution
|
|
691
|
+
* @param options - Optional configuration including tools and abort signal
|
|
692
|
+
* @returns An async generator of stream events
|
|
693
|
+
*
|
|
694
|
+
* @example
|
|
695
|
+
* ```typescript
|
|
696
|
+
* // Start execution
|
|
697
|
+
* for await (const event of client.workers.execute(agentId, input)) {
|
|
698
|
+
* if (event.type === 'client-tool-request') {
|
|
699
|
+
* // Execute tools client-side
|
|
700
|
+
* const results = await executeToolsClientSide(event.toolCalls);
|
|
701
|
+
* // Continue execution
|
|
702
|
+
* for await (const ev of client.workers.continue(agentId, event.executionId, results)) {
|
|
703
|
+
* // Handle remaining events
|
|
704
|
+
* }
|
|
705
|
+
* }
|
|
706
|
+
* }
|
|
707
|
+
* ```
|
|
708
|
+
*/
|
|
709
|
+
async *continue(agentId, executionId, toolResults, options = {}) {
|
|
710
|
+
yield* executeStream(
|
|
711
|
+
{
|
|
712
|
+
config: this.config,
|
|
713
|
+
toolHandlers: options.tools ?? {},
|
|
714
|
+
url: `${this.config.baseUrl}/api/agents/${agentId}/execute`,
|
|
715
|
+
buildBody: ({ executionId: execId, toolResults: results }) => ({
|
|
716
|
+
type: "continue",
|
|
717
|
+
executionId: execId ?? executionId,
|
|
718
|
+
toolResults: results ?? toolResults
|
|
719
|
+
}),
|
|
720
|
+
errorContext: "Failed to continue worker"
|
|
721
|
+
},
|
|
722
|
+
{ executionId, toolResults },
|
|
723
|
+
options.signal
|
|
724
|
+
);
|
|
725
|
+
}
|
|
726
|
+
};
|
|
727
|
+
|
|
598
728
|
// src/client.ts
|
|
599
729
|
var OctavusClient = class {
|
|
600
730
|
agents;
|
|
601
731
|
agentSessions;
|
|
602
732
|
files;
|
|
733
|
+
workers;
|
|
603
734
|
baseUrl;
|
|
604
735
|
apiKey;
|
|
605
736
|
constructor(config) {
|
|
@@ -612,6 +743,7 @@ var OctavusClient = class {
|
|
|
612
743
|
this.agents = new AgentsApi(apiConfig);
|
|
613
744
|
this.agentSessions = new AgentSessionsApi(apiConfig);
|
|
614
745
|
this.files = new FilesApi(apiConfig);
|
|
746
|
+
this.workers = new WorkersApi(apiConfig);
|
|
615
747
|
}
|
|
616
748
|
getHeaders() {
|
|
617
749
|
const headers = {
|
|
@@ -644,7 +776,7 @@ import {
|
|
|
644
776
|
isValidationError,
|
|
645
777
|
createErrorEvent,
|
|
646
778
|
errorToStreamEvent,
|
|
647
|
-
createInternalErrorEvent as
|
|
779
|
+
createInternalErrorEvent as createInternalErrorEvent3,
|
|
648
780
|
createApiErrorEvent as createApiErrorEvent2,
|
|
649
781
|
generateId,
|
|
650
782
|
isAbortError as isAbortError2,
|
|
@@ -678,9 +810,10 @@ export {
|
|
|
678
810
|
OctavusError,
|
|
679
811
|
Resource,
|
|
680
812
|
ValidationError,
|
|
813
|
+
WorkersApi,
|
|
681
814
|
createApiErrorEvent2 as createApiErrorEvent,
|
|
682
815
|
createErrorEvent,
|
|
683
|
-
|
|
816
|
+
createInternalErrorEvent3 as createInternalErrorEvent,
|
|
684
817
|
errorToStreamEvent,
|
|
685
818
|
generateId,
|
|
686
819
|
getSkillSlugFromToolCall,
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/api-error.ts","../src/base-api-client.ts","../src/agent-types.ts","../src/agents.ts","../src/agent-sessions.ts","../src/session.ts","../src/files.ts","../src/client.ts","../src/resource.ts","../src/index.ts"],"sourcesContent":["import { z } from 'zod';\n\nconst ApiErrorResponseSchema = z.object({\n error: z.string().optional(),\n message: z.string().optional(),\n code: z.string().optional(),\n});\n\n/**\n * Error thrown when API request fails\n */\nexport class ApiError extends Error {\n constructor(\n message: string,\n public status: number,\n public code?: string,\n ) {\n super(message);\n this.name = 'ApiError';\n }\n}\n\ninterface ParsedApiError {\n message: string;\n code?: string;\n}\n\n/**\n * Parse error from API response using Zod\n */\nexport async function parseApiError(\n response: Response,\n defaultMessage: string,\n): Promise<ParsedApiError> {\n const fallbackMessage = `${defaultMessage}: ${response.statusText}`;\n\n try {\n const json: unknown = await response.json();\n const parsed = ApiErrorResponseSchema.safeParse(json);\n\n if (parsed.success) {\n return {\n message: parsed.data.error ?? parsed.data.message ?? fallbackMessage,\n code: parsed.data.code,\n };\n }\n } catch {\n // Use default message\n }\n\n return { message: fallbackMessage };\n}\n\n/**\n * Parse error from API response and throw ApiError\n */\nexport async function throwApiError(response: Response, defaultMessage: string): Promise<never> {\n const { message, code } = await parseApiError(response, defaultMessage);\n throw new ApiError(message, response.status, code);\n}\n","import type { ZodType } from 'zod';\nimport { throwApiError } from '@/api-error.js';\n\nexport { ApiError } from '@/api-error.js';\n\nexport interface ApiClientConfig {\n baseUrl: string;\n getHeaders: () => Record<string, string>;\n}\n\n/** Base class for API clients with shared HTTP utilities */\nexport abstract class BaseApiClient {\n protected readonly config: ApiClientConfig;\n\n constructor(config: ApiClientConfig) {\n this.config = config;\n }\n\n protected async httpGet<T>(path: string, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'GET',\n headers: this.config.getHeaders(),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n\n protected async httpPost<T>(path: string, body: unknown, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'POST',\n headers: this.config.getHeaders(),\n body: JSON.stringify(body),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n\n protected async httpPatch<T>(path: string, body: unknown, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'PATCH',\n headers: this.config.getHeaders(),\n body: JSON.stringify(body),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n}\n","import { z } from 'zod';\n\n/** Agent format - interactive (chat) or worker (background task) */\nexport type AgentFormat = 'interactive' | 'worker';\n\n/** Agent settings */\nexport interface AgentSettings {\n slug: string;\n name: string;\n description?: string;\n format: AgentFormat;\n}\n\n/** Agent prompt */\nexport interface AgentPrompt {\n name: string;\n content: string;\n}\n\n/**\n * Agent summary returned from list endpoint\n */\nexport interface Agent {\n /** Agent slug (human-readable identifier within project) */\n slug: string;\n /** Agent ID - use this for API calls */\n id: string;\n name: string;\n description: string | null;\n format: AgentFormat;\n createdAt: string;\n updatedAt: string;\n projectId: string;\n}\n\n/**\n * Full agent definition returned from get endpoint\n */\nexport interface AgentDefinition {\n settings: AgentSettings;\n protocol: string;\n prompts: AgentPrompt[];\n /** Agent ID - use this for API calls like createSession */\n id: string;\n}\n\n// Schemas\n\nexport const agentFormatSchema = z.enum(['interactive', 'worker']);\n\nconst agentSettingsSchema = z.object({\n slug: z.string(),\n name: z.string(),\n description: z.string().optional(),\n format: agentFormatSchema,\n});\n\nconst agentPromptSchema = z.object({\n name: z.string(),\n content: z.string(),\n});\n\nexport const agentSchema = z.object({\n slug: z.string(),\n id: z.string(),\n name: z.string(),\n description: z.string().nullable(),\n format: agentFormatSchema,\n createdAt: z.string(),\n updatedAt: z.string(),\n projectId: z.string(),\n});\n\nexport const agentsResponseSchema = z.object({\n agents: z.array(agentSchema),\n});\n\nexport const agentDefinitionSchema = z.object({\n settings: agentSettingsSchema,\n protocol: z.string(),\n prompts: z.array(agentPromptSchema),\n id: z.string(),\n});\n","import { BaseApiClient } from '@/base-api-client.js';\nimport {\n agentsResponseSchema,\n agentDefinitionSchema,\n type Agent,\n type AgentDefinition,\n} from '@/agent-types.js';\n\n/**\n * API for listing and retrieving agent definitions.\n *\n * Note: Agent management (create, update, sync) should be done via the @octavus/cli package.\n * This API uses agent IDs only - use CLI for slug-based operations.\n */\nexport class AgentsApi extends BaseApiClient {\n /** List all agents in the project */\n async list(): Promise<Agent[]> {\n const response = await this.httpGet('/api/agents', agentsResponseSchema);\n return response.agents;\n }\n\n /** Get a single agent by ID */\n async get(agentId: string): Promise<AgentDefinition> {\n return await this.httpGet(`/api/agents/${agentId}`, agentDefinitionSchema);\n }\n}\n","import { z } from 'zod';\nimport {\n chatMessageSchema,\n uiMessageSchema,\n type ChatMessage,\n type ToolHandlers,\n type UIMessage,\n} from '@octavus/core';\nimport { BaseApiClient } from '@/base-api-client.js';\nimport { throwApiError } from '@/api-error.js';\nimport { AgentSession } from '@/session.js';\nimport type { Resource } from '@/resource.js';\n\nconst createSessionResponseSchema = z.object({\n sessionId: z.string(),\n});\n\nconst sessionStateSchema = z.object({\n id: z.string(),\n agentId: z.string(),\n input: z.record(z.string(), z.unknown()),\n variables: z.record(z.string(), z.unknown()),\n resources: z.record(z.string(), z.unknown()),\n messages: z.array(chatMessageSchema),\n status: z.literal('active').optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n});\n\nconst uiSessionResponseSchema = z.object({\n sessionId: z.string(),\n agentId: z.string(),\n messages: z.array(uiMessageSchema),\n status: z.literal('active').optional(),\n});\n\nconst expiredSessionResponseSchema = z.object({\n sessionId: z.string(),\n agentId: z.string(),\n status: z.literal('expired'),\n createdAt: z.string(),\n});\n\nconst restoreSessionResponseSchema = z.object({\n sessionId: z.string(),\n restored: z.boolean(),\n});\n\n/** Session status indicating whether it's active or expired */\nexport type SessionStatus = 'active' | 'expired';\n\nexport interface SessionState {\n id: string;\n agentId: string;\n input: Record<string, unknown>;\n variables: Record<string, unknown>;\n resources: Record<string, unknown>;\n messages: ChatMessage[];\n status?: 'active';\n createdAt: string;\n updatedAt: string;\n}\n\nexport interface UISessionState {\n sessionId: string;\n agentId: string;\n messages: UIMessage[];\n status?: 'active';\n}\n\nexport interface ExpiredSessionState {\n sessionId: string;\n agentId: string;\n status: 'expired';\n createdAt: string;\n}\n\nexport interface RestoreSessionResult {\n sessionId: string;\n /** True if session was restored from messages, false if already active */\n restored: boolean;\n}\n\nexport interface SessionAttachOptions {\n tools?: ToolHandlers;\n resources?: Resource[];\n}\n\n/** API for managing agent sessions */\nexport class AgentSessionsApi extends BaseApiClient {\n /** Create a new session for an agent */\n async create(agentId: string, input?: Record<string, unknown>): Promise<string> {\n const response = await this.httpPost(\n '/api/agent-sessions',\n { agentId, input },\n createSessionResponseSchema,\n );\n return response.sessionId;\n }\n\n /**\n * Get full session state (for internal/debug use)\n * Note: Contains all messages including hidden content\n *\n * Returns SessionState for active sessions, ExpiredSessionState for expired sessions.\n * Check `status` field to determine which type was returned.\n */\n async get(sessionId: string): Promise<SessionState | ExpiredSessionState> {\n const response = await fetch(`${this.config.baseUrl}/api/agent-sessions/${sessionId}`, {\n method: 'GET',\n headers: this.config.getHeaders(),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n\n const expiredResult = expiredSessionResponseSchema.safeParse(data);\n if (expiredResult.success) {\n return expiredResult.data;\n }\n\n return sessionStateSchema.parse(data);\n }\n\n /**\n * Get UI-ready session messages (for client display)\n * Returns only visible messages with hidden content filtered out.\n *\n * For expired sessions, returns status: 'expired' without messages.\n * Use restore() to restore from stored messages before continuing.\n */\n async getMessages(sessionId: string): Promise<UISessionState | ExpiredSessionState> {\n const response = await fetch(\n `${this.config.baseUrl}/api/agent-sessions/${sessionId}?format=ui`,\n {\n method: 'GET',\n headers: this.config.getHeaders(),\n },\n );\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n\n const expiredResult = expiredSessionResponseSchema.safeParse(data);\n if (expiredResult.success) {\n return expiredResult.data;\n }\n\n return uiSessionResponseSchema.parse(data);\n }\n\n /**\n * Restore an expired session from stored messages.\n *\n * Use this to restore a session after its state has expired.\n * The consumer should have stored the UIMessage[] array from previous interactions.\n *\n * @param sessionId - The session ID to restore\n * @param messages - Previously stored UIMessage[] array\n * @param input - Optional session input for system prompt interpolation (same as create)\n * @returns { sessionId, restored: true } if restored, { sessionId, restored: false } if already active\n */\n async restore(\n sessionId: string,\n messages: UIMessage[],\n input?: Record<string, unknown>,\n ): Promise<RestoreSessionResult> {\n return await this.httpPost(\n `/api/agent-sessions/${sessionId}/restore`,\n { messages, input },\n restoreSessionResponseSchema,\n );\n }\n\n /** Attach to an existing session for triggering events */\n attach(sessionId: string, options: SessionAttachOptions = {}): AgentSession {\n return new AgentSession({\n sessionId,\n config: this.config,\n tools: options.tools,\n resources: options.resources,\n });\n }\n}\n","import {\n safeParseStreamEvent,\n isAbortError,\n createInternalErrorEvent,\n createApiErrorEvent,\n type StreamEvent,\n type ToolHandlers,\n type PendingToolCall,\n type ToolResult,\n} from '@octavus/core';\nimport { parseApiError } from '@/api-error.js';\nimport type { ApiClientConfig } from '@/base-api-client.js';\nimport type { Resource } from '@/resource.js';\n\n// =============================================================================\n// Request Types\n// =============================================================================\n\n/** Start a new trigger execution */\nexport interface TriggerRequest {\n type: 'trigger';\n triggerName: string;\n input?: Record<string, unknown>;\n}\n\n/** Continue execution after client-side tool handling */\nexport interface ContinueRequest {\n type: 'continue';\n executionId: string;\n toolResults: ToolResult[];\n}\n\n/** All request types supported by the session */\nexport type SessionRequest = TriggerRequest | ContinueRequest;\n\n/** Stop message to abort in-flight requests */\nexport interface StopMessage {\n type: 'stop';\n}\n\n/** All socket protocol messages (trigger, continue, stop) */\nexport type SocketMessage = TriggerRequest | ContinueRequest | StopMessage;\n\n// =============================================================================\n// Socket Message Handler Types\n// =============================================================================\n\n/** Handlers for socket message streaming */\nexport interface SocketMessageHandlers {\n /** Called for each stream event */\n onEvent: (event: StreamEvent) => void;\n /** Called after streaming completes (not called if aborted) */\n onFinish?: () => void | Promise<void>;\n}\n\n/**\n * Converts an async iterable of stream events to an SSE-formatted ReadableStream.\n * Use this when you need to return an SSE response (e.g., HTTP endpoints).\n *\n * @example\n * ```typescript\n * const events = session.trigger('user-message', input);\n * return new Response(toSSEStream(events), {\n * headers: { 'Content-Type': 'text/event-stream' },\n * });\n * ```\n */\nexport function toSSEStream(events: AsyncIterable<StreamEvent>): ReadableStream<Uint8Array> {\n const encoder = new TextEncoder();\n\n return new ReadableStream({\n async start(controller) {\n try {\n for await (const event of events) {\n controller.enqueue(encoder.encode(`data: ${JSON.stringify(event)}\\n\\n`));\n }\n controller.enqueue(encoder.encode('data: [DONE]\\n\\n'));\n controller.close();\n } catch (err) {\n const errorEvent = createInternalErrorEvent(\n err instanceof Error ? err.message : 'Unknown error',\n );\n controller.enqueue(encoder.encode(`data: ${JSON.stringify(errorEvent)}\\n\\n`));\n controller.close();\n }\n },\n });\n}\n\nexport interface SessionConfig {\n sessionId: string;\n config: ApiClientConfig;\n tools?: ToolHandlers;\n resources?: Resource[];\n}\n\n/**\n * Options for trigger execution.\n */\nexport interface TriggerOptions {\n /** Abort signal to cancel the trigger execution */\n signal?: AbortSignal;\n}\n\n/** Handles streaming and tool continuation for agent sessions */\nexport class AgentSession {\n private sessionId: string;\n private config: ApiClientConfig;\n private toolHandlers: ToolHandlers;\n private resourceMap: Map<string, Resource>;\n private socketAbortController: AbortController | null = null;\n\n constructor(sessionConfig: SessionConfig) {\n this.sessionId = sessionConfig.sessionId;\n this.config = sessionConfig.config;\n this.toolHandlers = sessionConfig.tools ?? {};\n this.resourceMap = new Map();\n\n // Index resources by name for fast lookup\n for (const resource of sessionConfig.resources ?? []) {\n this.resourceMap.set(resource.name, resource);\n }\n }\n\n /**\n * Execute a session request and stream the response.\n *\n * This is the unified method that handles both triggers and continuations.\n * Use this when you want to pass through requests from the client directly.\n *\n * @param request - The request (check `request.type` for the kind)\n * @param options - Optional configuration including abort signal\n *\n * @example HTTP route (simple passthrough)\n * ```typescript\n * const events = session.execute(body, { signal: request.signal });\n * return new Response(toSSEStream(events));\n * ```\n *\n * @example WebSocket handler\n * ```typescript\n * socket.on('message', (data) => {\n * const events = session.execute(data);\n * for await (const event of events) {\n * socket.send(JSON.stringify(event));\n * }\n * });\n * ```\n */\n async *execute(request: SessionRequest, options?: TriggerOptions): AsyncGenerator<StreamEvent> {\n if (request.type === 'continue') {\n yield* this.executeStream(\n { executionId: request.executionId, toolResults: request.toolResults },\n options?.signal,\n );\n } else {\n yield* this.executeStream(\n { triggerName: request.triggerName, input: request.input },\n options?.signal,\n );\n }\n }\n\n getSessionId(): string {\n return this.sessionId;\n }\n\n /**\n * Handle a WebSocket protocol message (trigger, continue, or stop).\n * Manages abort controller lifecycle internally.\n *\n * @example\n * ```typescript\n * conn.on('data', (raw) => {\n * session.handleSocketMessage(JSON.parse(raw), {\n * onEvent: (event) => conn.write(JSON.stringify(event)),\n * onFinish: () => sendMessagesUpdate(),\n * });\n * });\n * ```\n */\n async handleSocketMessage(\n message: SocketMessage,\n handlers: SocketMessageHandlers,\n ): Promise<void> {\n if (message.type === 'stop') {\n this.socketAbortController?.abort();\n return;\n }\n\n // Abort any previous request before starting new one\n this.socketAbortController?.abort();\n this.socketAbortController = new AbortController();\n\n // Capture local reference - controller might change if another request comes in\n const localController = this.socketAbortController;\n\n try {\n const events = this.execute(message, { signal: localController.signal });\n\n for await (const event of events) {\n if (localController.signal.aborted) break;\n handlers.onEvent(event);\n }\n\n if (!localController.signal.aborted && handlers.onFinish) {\n await handlers.onFinish();\n }\n } catch (err) {\n if (!localController.signal.aborted) {\n const errorEvent = createInternalErrorEvent(\n err instanceof Error ? err.message : 'Unknown error',\n );\n handlers.onEvent(errorEvent);\n }\n }\n }\n\n private async *executeStream(\n payload: {\n triggerName?: string;\n input?: Record<string, unknown>;\n executionId?: string;\n toolResults?: ToolResult[];\n },\n signal?: AbortSignal,\n ): AsyncGenerator<StreamEvent> {\n let toolResults = payload.toolResults;\n let executionId = payload.executionId;\n let continueLoop = true;\n\n while (continueLoop) {\n // Check if aborted before making request\n if (signal?.aborted) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n // Build request body - only include defined fields\n const body: Record<string, unknown> = {};\n if (payload.triggerName !== undefined) body.triggerName = payload.triggerName;\n if (payload.input !== undefined) body.input = payload.input;\n if (executionId !== undefined) body.executionId = executionId;\n if (toolResults !== undefined) body.toolResults = toolResults;\n\n // Make request to platform\n let response: Response;\n try {\n response = await fetch(\n `${this.config.baseUrl}/api/agent-sessions/${this.sessionId}/trigger`,\n {\n method: 'POST',\n headers: this.config.getHeaders(),\n body: JSON.stringify(body),\n signal,\n },\n );\n } catch (err) {\n // Handle abort errors gracefully\n if (isAbortError(err)) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n throw err;\n }\n\n if (!response.ok) {\n const { message } = await parseApiError(response, 'Failed to trigger');\n yield createApiErrorEvent(response.status, message);\n return;\n }\n\n if (!response.body) {\n yield createInternalErrorEvent('Response body is not readable');\n return;\n }\n\n // Reset tool results for next iteration (executionId persists through the loop)\n toolResults = undefined;\n\n // Read and process the SSE stream\n const reader = response.body.getReader();\n const decoder = new TextDecoder();\n let buffer = '';\n let pendingToolCalls: PendingToolCall[] | null = null;\n\n // Read stream until done\n let streamDone = false;\n while (!streamDone) {\n // Check if aborted during stream reading\n if (signal?.aborted) {\n reader.releaseLock();\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n let readResult: ReadableStreamReadResult<Uint8Array>;\n try {\n readResult = await reader.read();\n } catch (err) {\n // Handle abort errors gracefully during read\n if (isAbortError(err)) {\n reader.releaseLock();\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n throw err;\n }\n\n const { done, value } = readResult;\n\n if (done) {\n streamDone = true;\n continue;\n }\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split('\\n');\n buffer = lines.pop() ?? '';\n\n for (const line of lines) {\n if (line.startsWith('data: ') && line !== 'data: [DONE]') {\n try {\n const parsed = safeParseStreamEvent(JSON.parse(line.slice(6)));\n if (!parsed.success) {\n // Skip malformed events\n continue;\n }\n const event = parsed.data;\n\n // Capture executionId from start event\n if (event.type === 'start' && event.executionId) {\n executionId = event.executionId;\n }\n\n // Handle tool-request - split into server and client tools\n if (event.type === 'tool-request') {\n pendingToolCalls = event.toolCalls;\n // Don't forward tool-request to consumer\n continue;\n }\n\n if (event.type === 'finish') {\n if (event.finishReason === 'tool-calls' && pendingToolCalls) {\n continue;\n }\n yield event;\n continueLoop = false;\n continue;\n }\n\n if (event.type === 'resource-update') {\n this.handleResourceUpdate(event.name, event.value);\n }\n\n yield event;\n } catch {\n // Skip malformed JSON\n }\n }\n }\n }\n\n // Check if aborted before tool execution\n if (signal?.aborted) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n // If we have pending tool calls, split into server and client tools\n if (pendingToolCalls && pendingToolCalls.length > 0) {\n const serverTools = pendingToolCalls.filter((tc) => this.toolHandlers[tc.toolName]);\n const clientTools = pendingToolCalls.filter((tc) => !this.toolHandlers[tc.toolName]);\n\n const serverResults = await Promise.all(\n serverTools.map(async (tc): Promise<ToolResult> => {\n // Handler is guaranteed to exist since we filtered by handler presence\n const handler = this.toolHandlers[tc.toolName]!;\n try {\n const result = await handler(tc.args);\n return {\n toolCallId: tc.toolCallId,\n toolName: tc.toolName,\n result,\n outputVariable: tc.outputVariable,\n blockIndex: tc.blockIndex,\n };\n } catch (err) {\n return {\n toolCallId: tc.toolCallId,\n toolName: tc.toolName,\n error: err instanceof Error ? err.message : 'Tool execution failed',\n outputVariable: tc.outputVariable,\n blockIndex: tc.blockIndex,\n };\n }\n }),\n );\n\n // Emit tool-output events for server tools immediately\n for (const tr of serverResults) {\n if (tr.error) {\n yield { type: 'tool-output-error', toolCallId: tr.toolCallId, error: tr.error };\n } else {\n yield { type: 'tool-output-available', toolCallId: tr.toolCallId, output: tr.result };\n }\n }\n\n // If there are client tools, emit client-tool-request and stop the loop\n if (clientTools.length > 0) {\n if (!executionId) {\n yield createInternalErrorEvent('Missing executionId for client-tool-request');\n return;\n }\n // Include executionId and server results in event\n yield {\n type: 'client-tool-request',\n executionId,\n toolCalls: clientTools,\n serverToolResults: serverResults.length > 0 ? serverResults : undefined,\n };\n yield { type: 'finish', finishReason: 'client-tool-calls', executionId };\n continueLoop = false;\n } else {\n // All tools handled server-side, continue loop\n toolResults = serverResults;\n }\n } else {\n // No pending tools, we're done\n continueLoop = false;\n }\n }\n }\n\n private handleResourceUpdate(name: string, value: unknown): void {\n const resource = this.resourceMap.get(name);\n if (resource) {\n void resource.onUpdate(value);\n }\n }\n}\n","import { z } from 'zod';\nimport { BaseApiClient } from '@/base-api-client.js';\n\n// =============================================================================\n// Schemas\n// =============================================================================\n\n/**\n * Schema for a single file upload request\n */\nexport const fileUploadRequestSchema = z.object({\n filename: z.string().min(1).max(255),\n mediaType: z.string().min(1),\n size: z.number().int().positive(),\n});\n\n/**\n * Schema for a single file upload response\n */\nexport const fileUploadInfoSchema = z.object({\n /** File ID to reference in messages */\n id: z.string(),\n /** Presigned PUT URL for uploading to S3 */\n uploadUrl: z.url(),\n /** Presigned GET URL for downloading after upload */\n downloadUrl: z.url(),\n});\n\n/**\n * Schema for the upload URLs response\n */\nexport const uploadUrlsResponseSchema = z.object({\n files: z.array(fileUploadInfoSchema),\n});\n\n// =============================================================================\n// Types\n// =============================================================================\n\nexport type FileUploadRequest = z.infer<typeof fileUploadRequestSchema>;\nexport type FileUploadInfo = z.infer<typeof fileUploadInfoSchema>;\nexport type UploadUrlsResponse = z.infer<typeof uploadUrlsResponseSchema>;\n\n// =============================================================================\n// API\n// =============================================================================\n\n/**\n * API for file operations.\n *\n * Provides methods to generate presigned URLs for file uploads.\n * Files are uploaded directly to S3, not through the platform.\n *\n * @example\n * ```typescript\n * // Get upload URLs\n * const { files } = await client.files.getUploadUrls(sessionId, [\n * { filename: 'image.png', mediaType: 'image/png', size: 12345 }\n * ]);\n *\n * // Upload directly to S3\n * await fetch(files[0].uploadUrl, {\n * method: 'PUT',\n * body: imageFile,\n * headers: { 'Content-Type': 'image/png' }\n * });\n *\n * // Use downloadUrl as FileReference in trigger input\n * ```\n */\nexport class FilesApi extends BaseApiClient {\n /**\n * Get presigned URLs for uploading files to a session.\n *\n * Returns upload URLs (PUT) and download URLs (GET) for each file.\n * Upload URLs expire in 15 minutes, download URLs match session TTL (24 hours).\n *\n * @param sessionId - The session ID to associate files with\n * @param files - Array of file metadata (filename, mediaType, size)\n * @returns Upload info with presigned URLs for each file\n *\n * @throws ApiError if session doesn't exist or validation fails\n *\n * @example\n * ```typescript\n * const { files } = await client.files.getUploadUrls(sessionId, [\n * { filename: 'photo.jpg', mediaType: 'image/jpeg', size: 102400 },\n * { filename: 'doc.pdf', mediaType: 'application/pdf', size: 204800 },\n * ]);\n *\n * // files[0].id - Use in FileReference\n * // files[0].uploadUrl - PUT to this URL\n * // files[0].downloadUrl - Use as FileReference.url\n * ```\n */\n async getUploadUrls(sessionId: string, files: FileUploadRequest[]): Promise<UploadUrlsResponse> {\n return await this.httpPost(\n '/api/files/upload-urls',\n { sessionId, files },\n uploadUrlsResponseSchema,\n );\n }\n}\n","import type { ApiClientConfig } from '@/base-api-client.js';\nimport { AgentsApi } from '@/agents.js';\nimport { AgentSessionsApi } from '@/agent-sessions.js';\nimport { FilesApi } from '@/files.js';\n\nexport interface OctavusClientConfig {\n baseUrl: string;\n apiKey?: string;\n}\n\n/** Client for interacting with the Octavus platform API */\nexport class OctavusClient {\n readonly agents: AgentsApi;\n readonly agentSessions: AgentSessionsApi;\n readonly files: FilesApi;\n readonly baseUrl: string;\n private readonly apiKey?: string;\n\n constructor(config: OctavusClientConfig) {\n this.baseUrl = config.baseUrl.replace(/\\/$/, '');\n this.apiKey = config.apiKey;\n\n const apiConfig: ApiClientConfig = {\n baseUrl: this.baseUrl,\n getHeaders: () => this.getHeaders(),\n };\n\n this.agents = new AgentsApi(apiConfig);\n this.agentSessions = new AgentSessionsApi(apiConfig);\n this.files = new FilesApi(apiConfig);\n }\n\n getHeaders(): Record<string, string> {\n const headers: Record<string, string> = {\n 'Content-Type': 'application/json',\n };\n\n if (this.apiKey) {\n headers.Authorization = `Bearer ${this.apiKey}`;\n }\n\n return headers;\n }\n}\n","/**\n * Base class for agent-managed resources.\n * Extend this class to define how each resource should be persisted when the agent updates it.\n */\nexport abstract class Resource {\n /** The resource name as defined in the agent protocol */\n abstract readonly name: string;\n\n /** Called when the agent updates this resource */\n abstract onUpdate(value: unknown): Promise<void> | void;\n}\n","export { OctavusClient, type OctavusClientConfig } from '@/client.js';\nexport { AgentsApi } from '@/agents.js';\nexport {\n AgentSessionsApi,\n type SessionState,\n type UISessionState,\n type ExpiredSessionState,\n type RestoreSessionResult,\n type SessionStatus,\n type SessionAttachOptions,\n} from '@/agent-sessions.js';\nexport {\n FilesApi,\n type FileUploadRequest,\n type FileUploadInfo,\n type UploadUrlsResponse,\n} from '@/files.js';\nexport {\n AgentSession,\n toSSEStream,\n type SessionConfig,\n type TriggerOptions,\n type SessionRequest,\n type TriggerRequest,\n type ContinueRequest,\n type StopMessage,\n type SocketMessage,\n type SocketMessageHandlers,\n} from '@/session.js';\nexport { Resource } from '@/resource.js';\nexport { ApiError } from '@/api-error.js';\n\n// Agent types (read-only - use @octavus/cli for agent management)\nexport type {\n AgentFormat,\n AgentSettings,\n AgentPrompt,\n Agent,\n AgentDefinition,\n} from '@/agent-types.js';\n\nexport type * from '@octavus/core';\nexport {\n // Error classes\n AppError,\n NotFoundError,\n ValidationError,\n ConflictError,\n ForbiddenError,\n OctavusError,\n // Error type guards\n isRateLimitError,\n isAuthenticationError,\n isProviderError,\n isToolError,\n isRetryableError,\n isValidationError,\n // Error event helpers\n createErrorEvent,\n errorToStreamEvent,\n createInternalErrorEvent,\n createApiErrorEvent,\n // Utilities\n generateId,\n isAbortError,\n // Thread helpers\n MAIN_THREAD,\n resolveThread,\n isMainThread,\n threadForPart,\n isOtherThread,\n // Type guards\n isFileReference,\n isFileReferenceArray,\n // Safe parse helpers\n safeParseStreamEvent,\n safeParseUIMessage,\n safeParseUIMessages,\n // Skills\n OCTAVUS_SKILL_TOOLS,\n isOctavusSkillTool,\n getSkillSlugFromToolCall,\n} from '@octavus/core';\n"],"mappings":"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","names":["z","z","z","z","z","createInternalErrorEvent","createApiErrorEvent","isAbortError","safeParseStreamEvent"]}
|
|
1
|
+
{"version":3,"sources":["../src/api-error.ts","../src/base-api-client.ts","../src/agent-types.ts","../src/agents.ts","../src/agent-sessions.ts","../src/session.ts","../src/streaming.ts","../src/files.ts","../src/workers.ts","../src/client.ts","../src/resource.ts","../src/index.ts"],"sourcesContent":["import { z } from 'zod';\n\nconst ApiErrorResponseSchema = z.object({\n error: z.string().optional(),\n message: z.string().optional(),\n code: z.string().optional(),\n});\n\n/**\n * Error thrown when API request fails\n */\nexport class ApiError extends Error {\n constructor(\n message: string,\n public status: number,\n public code?: string,\n ) {\n super(message);\n this.name = 'ApiError';\n }\n}\n\ninterface ParsedApiError {\n message: string;\n code?: string;\n}\n\n/**\n * Parse error from API response using Zod\n */\nexport async function parseApiError(\n response: Response,\n defaultMessage: string,\n): Promise<ParsedApiError> {\n const fallbackMessage = `${defaultMessage}: ${response.statusText}`;\n\n try {\n const json: unknown = await response.json();\n const parsed = ApiErrorResponseSchema.safeParse(json);\n\n if (parsed.success) {\n return {\n message: parsed.data.error ?? parsed.data.message ?? fallbackMessage,\n code: parsed.data.code,\n };\n }\n } catch {\n // Use default message\n }\n\n return { message: fallbackMessage };\n}\n\n/**\n * Parse error from API response and throw ApiError\n */\nexport async function throwApiError(response: Response, defaultMessage: string): Promise<never> {\n const { message, code } = await parseApiError(response, defaultMessage);\n throw new ApiError(message, response.status, code);\n}\n","import type { ZodType } from 'zod';\nimport { throwApiError } from '@/api-error.js';\n\nexport { ApiError } from '@/api-error.js';\n\nexport interface ApiClientConfig {\n baseUrl: string;\n getHeaders: () => Record<string, string>;\n}\n\n/** Base class for API clients with shared HTTP utilities */\nexport abstract class BaseApiClient {\n protected readonly config: ApiClientConfig;\n\n constructor(config: ApiClientConfig) {\n this.config = config;\n }\n\n protected async httpGet<T>(path: string, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'GET',\n headers: this.config.getHeaders(),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n\n protected async httpPost<T>(path: string, body: unknown, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'POST',\n headers: this.config.getHeaders(),\n body: JSON.stringify(body),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n\n protected async httpPatch<T>(path: string, body: unknown, schema: ZodType<T>): Promise<T> {\n const response = await fetch(`${this.config.baseUrl}${path}`, {\n method: 'PATCH',\n headers: this.config.getHeaders(),\n body: JSON.stringify(body),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n return schema.parse(data);\n }\n}\n","import { z } from 'zod';\n\n/** Agent format - interactive (chat) or worker (background task) */\nexport type AgentFormat = 'interactive' | 'worker';\n\n/** Agent settings */\nexport interface AgentSettings {\n slug: string;\n name: string;\n description?: string;\n format: AgentFormat;\n}\n\n/** Agent prompt */\nexport interface AgentPrompt {\n name: string;\n content: string;\n}\n\n/**\n * Agent summary returned from list endpoint\n */\nexport interface Agent {\n /** Agent slug (human-readable identifier within project) */\n slug: string;\n /** Agent ID - use this for API calls */\n id: string;\n name: string;\n description: string | null;\n format: AgentFormat;\n createdAt: string;\n updatedAt: string;\n projectId: string;\n}\n\n/**\n * Full agent definition returned from get endpoint\n */\nexport interface AgentDefinition {\n settings: AgentSettings;\n protocol: string;\n prompts: AgentPrompt[];\n /** Agent ID - use this for API calls like createSession */\n id: string;\n}\n\n// Schemas\n\nexport const agentFormatSchema = z.enum(['interactive', 'worker']);\n\nconst agentSettingsSchema = z.object({\n slug: z.string(),\n name: z.string(),\n description: z.string().optional(),\n format: agentFormatSchema,\n});\n\nconst agentPromptSchema = z.object({\n name: z.string(),\n content: z.string(),\n});\n\nexport const agentSchema = z.object({\n slug: z.string(),\n id: z.string(),\n name: z.string(),\n description: z.string().nullable(),\n format: agentFormatSchema,\n createdAt: z.string(),\n updatedAt: z.string(),\n projectId: z.string(),\n});\n\nexport const agentsResponseSchema = z.object({\n agents: z.array(agentSchema),\n});\n\nexport const agentDefinitionSchema = z.object({\n settings: agentSettingsSchema,\n protocol: z.string(),\n prompts: z.array(agentPromptSchema),\n id: z.string(),\n});\n","import { BaseApiClient } from '@/base-api-client.js';\nimport {\n agentsResponseSchema,\n agentDefinitionSchema,\n type Agent,\n type AgentDefinition,\n} from '@/agent-types.js';\n\n/**\n * API for listing and retrieving agent definitions.\n *\n * Note: Agent management (create, update, sync) should be done via the @octavus/cli package.\n * This API uses agent IDs only - use CLI for slug-based operations.\n */\nexport class AgentsApi extends BaseApiClient {\n /** List all agents in the project */\n async list(): Promise<Agent[]> {\n const response = await this.httpGet('/api/agents', agentsResponseSchema);\n return response.agents;\n }\n\n /** Get a single agent by ID */\n async get(agentId: string): Promise<AgentDefinition> {\n return await this.httpGet(`/api/agents/${agentId}`, agentDefinitionSchema);\n }\n}\n","import { z } from 'zod';\nimport {\n chatMessageSchema,\n uiMessageSchema,\n type ChatMessage,\n type ToolHandlers,\n type UIMessage,\n} from '@octavus/core';\nimport { BaseApiClient } from '@/base-api-client.js';\nimport { throwApiError } from '@/api-error.js';\nimport { AgentSession } from '@/session.js';\nimport type { Resource } from '@/resource.js';\n\nconst createSessionResponseSchema = z.object({\n sessionId: z.string(),\n});\n\nconst sessionStateSchema = z.object({\n id: z.string(),\n agentId: z.string(),\n input: z.record(z.string(), z.unknown()),\n variables: z.record(z.string(), z.unknown()),\n resources: z.record(z.string(), z.unknown()),\n messages: z.array(chatMessageSchema),\n status: z.literal('active').optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n});\n\nconst uiSessionResponseSchema = z.object({\n sessionId: z.string(),\n agentId: z.string(),\n messages: z.array(uiMessageSchema),\n status: z.literal('active').optional(),\n});\n\nconst expiredSessionResponseSchema = z.object({\n sessionId: z.string(),\n agentId: z.string(),\n status: z.literal('expired'),\n createdAt: z.string(),\n});\n\nconst restoreSessionResponseSchema = z.object({\n sessionId: z.string(),\n restored: z.boolean(),\n});\n\n/** Session status indicating whether it's active or expired */\nexport type SessionStatus = 'active' | 'expired';\n\nexport interface SessionState {\n id: string;\n agentId: string;\n input: Record<string, unknown>;\n variables: Record<string, unknown>;\n resources: Record<string, unknown>;\n messages: ChatMessage[];\n status?: 'active';\n createdAt: string;\n updatedAt: string;\n}\n\nexport interface UISessionState {\n sessionId: string;\n agentId: string;\n messages: UIMessage[];\n status?: 'active';\n}\n\nexport interface ExpiredSessionState {\n sessionId: string;\n agentId: string;\n status: 'expired';\n createdAt: string;\n}\n\nexport interface RestoreSessionResult {\n sessionId: string;\n /** True if session was restored from messages, false if already active */\n restored: boolean;\n}\n\nexport interface SessionAttachOptions {\n tools?: ToolHandlers;\n resources?: Resource[];\n}\n\n/** API for managing agent sessions */\nexport class AgentSessionsApi extends BaseApiClient {\n /** Create a new session for an agent */\n async create(agentId: string, input?: Record<string, unknown>): Promise<string> {\n const response = await this.httpPost(\n '/api/agent-sessions',\n { agentId, input },\n createSessionResponseSchema,\n );\n return response.sessionId;\n }\n\n /**\n * Get full session state (for internal/debug use)\n * Note: Contains all messages including hidden content\n *\n * Returns SessionState for active sessions, ExpiredSessionState for expired sessions.\n * Check `status` field to determine which type was returned.\n */\n async get(sessionId: string): Promise<SessionState | ExpiredSessionState> {\n const response = await fetch(`${this.config.baseUrl}/api/agent-sessions/${sessionId}`, {\n method: 'GET',\n headers: this.config.getHeaders(),\n });\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n\n const expiredResult = expiredSessionResponseSchema.safeParse(data);\n if (expiredResult.success) {\n return expiredResult.data;\n }\n\n return sessionStateSchema.parse(data);\n }\n\n /**\n * Get UI-ready session messages (for client display)\n * Returns only visible messages with hidden content filtered out.\n *\n * For expired sessions, returns status: 'expired' without messages.\n * Use restore() to restore from stored messages before continuing.\n */\n async getMessages(sessionId: string): Promise<UISessionState | ExpiredSessionState> {\n const response = await fetch(\n `${this.config.baseUrl}/api/agent-sessions/${sessionId}?format=ui`,\n {\n method: 'GET',\n headers: this.config.getHeaders(),\n },\n );\n\n if (!response.ok) {\n await throwApiError(response, 'Request failed');\n }\n\n const data: unknown = await response.json();\n\n const expiredResult = expiredSessionResponseSchema.safeParse(data);\n if (expiredResult.success) {\n return expiredResult.data;\n }\n\n return uiSessionResponseSchema.parse(data);\n }\n\n /**\n * Restore an expired session from stored messages.\n *\n * Use this to restore a session after its state has expired.\n * The consumer should have stored the UIMessage[] array from previous interactions.\n *\n * @param sessionId - The session ID to restore\n * @param messages - Previously stored UIMessage[] array\n * @param input - Optional session input for system prompt interpolation (same as create)\n * @returns { sessionId, restored: true } if restored, { sessionId, restored: false } if already active\n */\n async restore(\n sessionId: string,\n messages: UIMessage[],\n input?: Record<string, unknown>,\n ): Promise<RestoreSessionResult> {\n return await this.httpPost(\n `/api/agent-sessions/${sessionId}/restore`,\n { messages, input },\n restoreSessionResponseSchema,\n );\n }\n\n /** Attach to an existing session for triggering events */\n attach(sessionId: string, options: SessionAttachOptions = {}): AgentSession {\n return new AgentSession({\n sessionId,\n config: this.config,\n tools: options.tools,\n resources: options.resources,\n });\n }\n}\n","import {\n createInternalErrorEvent,\n type StreamEvent,\n type ToolHandlers,\n type ToolResult,\n} from '@octavus/core';\nimport type { ApiClientConfig } from '@/base-api-client.js';\nimport type { Resource } from '@/resource.js';\nimport { executeStream } from '@/streaming.js';\n\n// =============================================================================\n// Request Types\n// =============================================================================\n\n/** Start a new trigger execution */\nexport interface TriggerRequest {\n type: 'trigger';\n triggerName: string;\n input?: Record<string, unknown>;\n}\n\n/** Continue execution after client-side tool handling */\nexport interface ContinueRequest {\n type: 'continue';\n executionId: string;\n toolResults: ToolResult[];\n}\n\n/** All request types supported by the session */\nexport type SessionRequest = TriggerRequest | ContinueRequest;\n\n/** Stop message to abort in-flight requests */\nexport interface StopMessage {\n type: 'stop';\n}\n\n/** All socket protocol messages (trigger, continue, stop) */\nexport type SocketMessage = TriggerRequest | ContinueRequest | StopMessage;\n\n// =============================================================================\n// Socket Message Handler Types\n// =============================================================================\n\n/** Handlers for socket message streaming */\nexport interface SocketMessageHandlers {\n /** Called for each stream event */\n onEvent: (event: StreamEvent) => void;\n /** Called after streaming completes (not called if aborted) */\n onFinish?: () => void | Promise<void>;\n}\n\n/**\n * Converts an async iterable of stream events to an SSE-formatted ReadableStream.\n * Use this when you need to return an SSE response (e.g., HTTP endpoints).\n *\n * @example\n * ```typescript\n * const events = session.trigger('user-message', input);\n * return new Response(toSSEStream(events), {\n * headers: { 'Content-Type': 'text/event-stream' },\n * });\n * ```\n */\nexport function toSSEStream(events: AsyncIterable<StreamEvent>): ReadableStream<Uint8Array> {\n const encoder = new TextEncoder();\n\n return new ReadableStream({\n async start(controller) {\n try {\n for await (const event of events) {\n controller.enqueue(encoder.encode(`data: ${JSON.stringify(event)}\\n\\n`));\n }\n controller.enqueue(encoder.encode('data: [DONE]\\n\\n'));\n controller.close();\n } catch (err) {\n const errorEvent = createInternalErrorEvent(\n err instanceof Error ? err.message : 'Unknown error',\n );\n controller.enqueue(encoder.encode(`data: ${JSON.stringify(errorEvent)}\\n\\n`));\n controller.close();\n }\n },\n });\n}\n\nexport interface SessionConfig {\n sessionId: string;\n config: ApiClientConfig;\n tools?: ToolHandlers;\n resources?: Resource[];\n}\n\n/**\n * Options for trigger execution.\n */\nexport interface TriggerOptions {\n /** Abort signal to cancel the trigger execution */\n signal?: AbortSignal;\n}\n\n/** Handles streaming and tool continuation for agent sessions */\nexport class AgentSession {\n private sessionId: string;\n private config: ApiClientConfig;\n private toolHandlers: ToolHandlers;\n private resourceMap: Map<string, Resource>;\n private socketAbortController: AbortController | null = null;\n\n constructor(sessionConfig: SessionConfig) {\n this.sessionId = sessionConfig.sessionId;\n this.config = sessionConfig.config;\n this.toolHandlers = sessionConfig.tools ?? {};\n this.resourceMap = new Map();\n\n for (const resource of sessionConfig.resources ?? []) {\n this.resourceMap.set(resource.name, resource);\n }\n }\n\n /**\n * Execute a session request and stream the response.\n *\n * This is the unified method that handles both triggers and continuations.\n * Use this when you want to pass through requests from the client directly.\n *\n * @param request - The request (check `request.type` for the kind)\n * @param options - Optional configuration including abort signal\n *\n * @example HTTP route (simple passthrough)\n * ```typescript\n * const events = session.execute(body, { signal: request.signal });\n * return new Response(toSSEStream(events));\n * ```\n *\n * @example WebSocket handler\n * ```typescript\n * socket.on('message', (data) => {\n * const events = session.execute(data);\n * for await (const event of events) {\n * socket.send(JSON.stringify(event));\n * }\n * });\n * ```\n */\n async *execute(request: SessionRequest, options?: TriggerOptions): AsyncGenerator<StreamEvent> {\n if (request.type === 'continue') {\n yield* this.executeStream(\n { executionId: request.executionId, toolResults: request.toolResults },\n options?.signal,\n );\n } else {\n yield* this.executeStream(\n { triggerName: request.triggerName, input: request.input },\n options?.signal,\n );\n }\n }\n\n getSessionId(): string {\n return this.sessionId;\n }\n\n /**\n * Handle a WebSocket protocol message (trigger, continue, or stop).\n * Manages abort controller lifecycle internally.\n *\n * @example\n * ```typescript\n * conn.on('data', (raw) => {\n * session.handleSocketMessage(JSON.parse(raw), {\n * onEvent: (event) => conn.write(JSON.stringify(event)),\n * onFinish: () => sendMessagesUpdate(),\n * });\n * });\n * ```\n */\n async handleSocketMessage(\n message: SocketMessage,\n handlers: SocketMessageHandlers,\n ): Promise<void> {\n if (message.type === 'stop') {\n this.socketAbortController?.abort();\n return;\n }\n\n this.socketAbortController?.abort();\n this.socketAbortController = new AbortController();\n\n const localController = this.socketAbortController;\n\n try {\n const events = this.execute(message, { signal: localController.signal });\n\n for await (const event of events) {\n if (localController.signal.aborted) break;\n handlers.onEvent(event);\n }\n\n if (!localController.signal.aborted && handlers.onFinish) {\n await handlers.onFinish();\n }\n } catch (err) {\n if (!localController.signal.aborted) {\n const errorEvent = createInternalErrorEvent(\n err instanceof Error ? err.message : 'Unknown error',\n );\n handlers.onEvent(errorEvent);\n }\n }\n }\n\n private async *executeStream(\n payload: {\n triggerName?: string;\n input?: Record<string, unknown>;\n executionId?: string;\n toolResults?: ToolResult[];\n },\n signal?: AbortSignal,\n ): AsyncGenerator<StreamEvent> {\n yield* executeStream(\n {\n config: this.config,\n toolHandlers: this.toolHandlers,\n url: `${this.config.baseUrl}/api/agent-sessions/${this.sessionId}/trigger`,\n buildBody: ({ executionId, toolResults }) => {\n const body: Record<string, unknown> = {};\n if (payload.triggerName !== undefined) body.triggerName = payload.triggerName;\n if (payload.input !== undefined) body.input = payload.input;\n if (executionId !== undefined) body.executionId = executionId;\n if (toolResults !== undefined) body.toolResults = toolResults;\n return body;\n },\n onResourceUpdate: (name, value) => this.handleResourceUpdate(name, value),\n errorContext: 'Failed to trigger',\n },\n { executionId: payload.executionId, toolResults: payload.toolResults },\n signal,\n );\n }\n\n private handleResourceUpdate(name: string, value: unknown): void {\n const resource = this.resourceMap.get(name);\n if (resource) {\n void resource.onUpdate(value);\n }\n }\n}\n","import {\n safeParseStreamEvent,\n isAbortError,\n createInternalErrorEvent,\n createApiErrorEvent,\n type StreamEvent,\n type ToolHandlers,\n type PendingToolCall,\n type ToolResult,\n} from '@octavus/core';\nimport { parseApiError } from '@/api-error.js';\nimport type { ApiClientConfig } from '@/base-api-client.js';\n\n/**\n * Configuration for streaming execution.\n */\nexport interface StreamExecutionConfig {\n /** API client config with baseUrl and headers */\n config: ApiClientConfig;\n /** Tool handlers for server-side execution */\n toolHandlers: ToolHandlers;\n /** Full URL to make the request to */\n url: string;\n /** Build the request body for this execution */\n buildBody: (state: {\n executionId?: string;\n toolResults?: ToolResult[];\n }) => Record<string, unknown>;\n /** Called when a resource-update event is received (optional) */\n onResourceUpdate?: (name: string, value: unknown) => void;\n /** Error message prefix for API errors */\n errorContext?: string;\n}\n\n/**\n * Initial payload for starting an execution stream.\n */\nexport interface StreamExecutionPayload {\n /** Initial execution ID (for continuation) */\n executionId?: string;\n /** Initial tool results (for continuation) */\n toolResults?: ToolResult[];\n}\n\n/**\n * Executes a streaming request with tool continuation support.\n *\n * This is the shared implementation for both interactive sessions and workers.\n * It handles:\n * - SSE stream parsing\n * - Abort signal handling\n * - Tool-request interception and server/client splitting\n * - Automatic continuation for server-handled tools\n * - Client-tool-request emission for client-handled tools\n */\nexport async function* executeStream(\n config: StreamExecutionConfig,\n payload: StreamExecutionPayload,\n signal?: AbortSignal,\n): AsyncGenerator<StreamEvent> {\n let toolResults = payload.toolResults;\n let executionId = payload.executionId;\n let continueLoop = true;\n\n while (continueLoop) {\n if (signal?.aborted) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n const body = config.buildBody({ executionId, toolResults });\n\n let response: Response;\n try {\n response = await fetch(config.url, {\n method: 'POST',\n headers: config.config.getHeaders(),\n body: JSON.stringify(body),\n signal,\n });\n } catch (err) {\n if (isAbortError(err)) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n throw err;\n }\n\n if (!response.ok) {\n const { message } = await parseApiError(response, config.errorContext ?? 'Request failed');\n yield createApiErrorEvent(response.status, message);\n return;\n }\n\n if (!response.body) {\n yield createInternalErrorEvent('Response body is not readable');\n return;\n }\n\n toolResults = undefined;\n\n const reader = response.body.getReader();\n const decoder = new TextDecoder();\n let buffer = '';\n let pendingToolCalls: PendingToolCall[] | null = null;\n\n let streamDone = false;\n while (!streamDone) {\n if (signal?.aborted) {\n reader.releaseLock();\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n let readResult: ReadableStreamReadResult<Uint8Array>;\n try {\n readResult = await reader.read();\n } catch (err) {\n if (isAbortError(err)) {\n reader.releaseLock();\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n throw err;\n }\n\n const { done, value } = readResult;\n\n if (done) {\n streamDone = true;\n continue;\n }\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split('\\n');\n buffer = lines.pop() ?? '';\n\n for (const line of lines) {\n if (line.startsWith('data: ') && line !== 'data: [DONE]') {\n try {\n const parsed = safeParseStreamEvent(JSON.parse(line.slice(6)));\n if (!parsed.success) {\n continue;\n }\n const event = parsed.data;\n\n if (event.type === 'start' && event.executionId) {\n executionId = event.executionId;\n }\n\n if (event.type === 'tool-request') {\n pendingToolCalls = event.toolCalls;\n continue;\n }\n\n if (event.type === 'finish') {\n if (event.finishReason === 'tool-calls' && pendingToolCalls) {\n continue;\n }\n yield event;\n continueLoop = false;\n continue;\n }\n\n if (event.type === 'resource-update' && config.onResourceUpdate) {\n config.onResourceUpdate(event.name, event.value);\n }\n\n yield event;\n } catch {\n // Skip malformed JSON\n }\n }\n }\n }\n\n if (signal?.aborted) {\n yield { type: 'finish', finishReason: 'stop' };\n return;\n }\n\n if (pendingToolCalls && pendingToolCalls.length > 0) {\n const serverTools = pendingToolCalls.filter((tc) => config.toolHandlers[tc.toolName]);\n const clientTools = pendingToolCalls.filter((tc) => !config.toolHandlers[tc.toolName]);\n\n const serverResults = await Promise.all(\n serverTools.map(async (tc): Promise<ToolResult> => {\n const handler = config.toolHandlers[tc.toolName]!;\n try {\n const result = await handler(tc.args);\n return {\n toolCallId: tc.toolCallId,\n toolName: tc.toolName,\n result,\n outputVariable: tc.outputVariable,\n blockIndex: tc.blockIndex,\n thread: tc.thread,\n workerId: tc.workerId,\n };\n } catch (err) {\n return {\n toolCallId: tc.toolCallId,\n toolName: tc.toolName,\n error: err instanceof Error ? err.message : 'Tool execution failed',\n outputVariable: tc.outputVariable,\n blockIndex: tc.blockIndex,\n thread: tc.thread,\n workerId: tc.workerId,\n };\n }\n }),\n );\n\n for (const tr of serverResults) {\n if (tr.error) {\n yield { type: 'tool-output-error', toolCallId: tr.toolCallId, error: tr.error };\n } else {\n yield { type: 'tool-output-available', toolCallId: tr.toolCallId, output: tr.result };\n }\n }\n\n if (clientTools.length > 0) {\n if (!executionId) {\n yield createInternalErrorEvent('Missing executionId for client-tool-request');\n return;\n }\n yield {\n type: 'client-tool-request',\n executionId,\n toolCalls: clientTools,\n serverToolResults: serverResults.length > 0 ? serverResults : undefined,\n };\n yield { type: 'finish', finishReason: 'client-tool-calls', executionId };\n continueLoop = false;\n } else {\n toolResults = serverResults;\n }\n } else {\n continueLoop = false;\n }\n }\n}\n","import { z } from 'zod';\nimport { BaseApiClient } from '@/base-api-client.js';\n\n// =============================================================================\n// Schemas\n// =============================================================================\n\n/**\n * Schema for a single file upload request\n */\nexport const fileUploadRequestSchema = z.object({\n filename: z.string().min(1).max(255),\n mediaType: z.string().min(1),\n size: z.number().int().positive(),\n});\n\n/**\n * Schema for a single file upload response\n */\nexport const fileUploadInfoSchema = z.object({\n /** File ID to reference in messages */\n id: z.string(),\n /** Presigned PUT URL for uploading to S3 */\n uploadUrl: z.url(),\n /** Presigned GET URL for downloading after upload */\n downloadUrl: z.url(),\n});\n\n/**\n * Schema for the upload URLs response\n */\nexport const uploadUrlsResponseSchema = z.object({\n files: z.array(fileUploadInfoSchema),\n});\n\n// =============================================================================\n// Types\n// =============================================================================\n\nexport type FileUploadRequest = z.infer<typeof fileUploadRequestSchema>;\nexport type FileUploadInfo = z.infer<typeof fileUploadInfoSchema>;\nexport type UploadUrlsResponse = z.infer<typeof uploadUrlsResponseSchema>;\n\n// =============================================================================\n// API\n// =============================================================================\n\n/**\n * API for file operations.\n *\n * Provides methods to generate presigned URLs for file uploads.\n * Files are uploaded directly to S3, not through the platform.\n *\n * @example\n * ```typescript\n * // Get upload URLs\n * const { files } = await client.files.getUploadUrls(sessionId, [\n * { filename: 'image.png', mediaType: 'image/png', size: 12345 }\n * ]);\n *\n * // Upload directly to S3\n * await fetch(files[0].uploadUrl, {\n * method: 'PUT',\n * body: imageFile,\n * headers: { 'Content-Type': 'image/png' }\n * });\n *\n * // Use downloadUrl as FileReference in trigger input\n * ```\n */\nexport class FilesApi extends BaseApiClient {\n /**\n * Get presigned URLs for uploading files to a session.\n *\n * Returns upload URLs (PUT) and download URLs (GET) for each file.\n * Upload URLs expire in 15 minutes, download URLs match session TTL (24 hours).\n *\n * @param sessionId - The session ID to associate files with\n * @param files - Array of file metadata (filename, mediaType, size)\n * @returns Upload info with presigned URLs for each file\n *\n * @throws ApiError if session doesn't exist or validation fails\n *\n * @example\n * ```typescript\n * const { files } = await client.files.getUploadUrls(sessionId, [\n * { filename: 'photo.jpg', mediaType: 'image/jpeg', size: 102400 },\n * { filename: 'doc.pdf', mediaType: 'application/pdf', size: 204800 },\n * ]);\n *\n * // files[0].id - Use in FileReference\n * // files[0].uploadUrl - PUT to this URL\n * // files[0].downloadUrl - Use as FileReference.url\n * ```\n */\n async getUploadUrls(sessionId: string, files: FileUploadRequest[]): Promise<UploadUrlsResponse> {\n return await this.httpPost(\n '/api/files/upload-urls',\n { sessionId, files },\n uploadUrlsResponseSchema,\n );\n }\n}\n","import type { StreamEvent, ToolHandlers, ToolResult } from '@octavus/core';\nimport { BaseApiClient } from '@/base-api-client.js';\nimport { executeStream } from '@/streaming.js';\n\n// =============================================================================\n// Request Types\n// =============================================================================\n\n/** Start a new worker execution */\nexport interface WorkerStartRequest {\n type: 'start';\n input: Record<string, unknown>;\n}\n\n/** Continue execution after client-side tool handling */\nexport interface WorkerContinueRequest {\n type: 'continue';\n executionId: string;\n toolResults: ToolResult[];\n}\n\n/** All request types supported by workers */\nexport type WorkerRequest = WorkerStartRequest | WorkerContinueRequest;\n\n// =============================================================================\n// Execution Options\n// =============================================================================\n\n/** Options for worker execution */\nexport interface WorkerExecuteOptions {\n /** Tool handlers for server-side tool execution */\n tools?: ToolHandlers;\n /** Abort signal to cancel the execution */\n signal?: AbortSignal;\n}\n\n// =============================================================================\n// Workers API\n// =============================================================================\n\n/** API for executing worker agents */\nexport class WorkersApi extends BaseApiClient {\n /**\n * Execute a worker agent and stream the response.\n *\n * Worker agents execute steps sequentially and return an output value.\n * Unlike interactive sessions, workers don't maintain persistent state.\n *\n * The execution handles the tool continuation pattern automatically:\n * - Server tools (with handlers provided) are executed automatically\n * - Client tools (without handlers) emit a client-tool-request event\n *\n * @param agentId - The worker agent ID\n * @param input - Input values for the worker\n * @param options - Optional configuration including tools and abort signal\n * @returns An async generator of stream events\n *\n * @example Basic execution\n * ```typescript\n * const events = client.workers.execute(agentId, { TOPIC: 'AI safety' });\n * for await (const event of events) {\n * if (event.type === 'worker-start') {\n * console.log(`Worker ${event.workerSlug} started (${event.workerId})`);\n * }\n * if (event.type === 'worker-result') {\n * if (event.error) {\n * console.error('Worker failed:', event.error);\n * } else {\n * console.log('Output:', event.output);\n * }\n * }\n * }\n * ```\n *\n * @example With tool handlers\n * ```typescript\n * const events = client.workers.execute(agentId, { TOPIC: 'AI safety' }, {\n * tools: {\n * 'web-search': async (args) => {\n * return await searchWeb(args.query);\n * },\n * },\n * });\n * ```\n */\n async *execute(\n agentId: string,\n input: Record<string, unknown>,\n options: WorkerExecuteOptions = {},\n ): AsyncGenerator<StreamEvent> {\n yield* executeStream(\n {\n config: this.config,\n toolHandlers: options.tools ?? {},\n url: `${this.config.baseUrl}/api/agents/${agentId}/execute`,\n buildBody: ({ executionId, toolResults }) =>\n !executionId ? { type: 'start', input } : { type: 'continue', executionId, toolResults },\n errorContext: 'Failed to execute worker',\n },\n {},\n options.signal,\n );\n }\n\n /**\n * Continue a worker execution after client-side tool handling.\n *\n * Use this when your worker has tools without server-side handlers.\n * The execution returns a client-tool-request event with an executionId.\n * Execute the tools client-side, then call this method to continue.\n *\n * @param agentId - The worker agent ID\n * @param executionId - The execution ID from the client-tool-request event\n * @param toolResults - Results from client-side tool execution\n * @param options - Optional configuration including tools and abort signal\n * @returns An async generator of stream events\n *\n * @example\n * ```typescript\n * // Start execution\n * for await (const event of client.workers.execute(agentId, input)) {\n * if (event.type === 'client-tool-request') {\n * // Execute tools client-side\n * const results = await executeToolsClientSide(event.toolCalls);\n * // Continue execution\n * for await (const ev of client.workers.continue(agentId, event.executionId, results)) {\n * // Handle remaining events\n * }\n * }\n * }\n * ```\n */\n async *continue(\n agentId: string,\n executionId: string,\n toolResults: ToolResult[],\n options: WorkerExecuteOptions = {},\n ): AsyncGenerator<StreamEvent> {\n yield* executeStream(\n {\n config: this.config,\n toolHandlers: options.tools ?? {},\n url: `${this.config.baseUrl}/api/agents/${agentId}/execute`,\n buildBody: ({ executionId: execId, toolResults: results }) => ({\n type: 'continue',\n executionId: execId ?? executionId,\n toolResults: results ?? toolResults,\n }),\n errorContext: 'Failed to continue worker',\n },\n { executionId, toolResults },\n options.signal,\n );\n }\n}\n","import type { ApiClientConfig } from '@/base-api-client.js';\nimport { AgentsApi } from '@/agents.js';\nimport { AgentSessionsApi } from '@/agent-sessions.js';\nimport { FilesApi } from '@/files.js';\nimport { WorkersApi } from '@/workers.js';\n\nexport interface OctavusClientConfig {\n baseUrl: string;\n apiKey?: string;\n}\n\n/** Client for interacting with the Octavus platform API */\nexport class OctavusClient {\n readonly agents: AgentsApi;\n readonly agentSessions: AgentSessionsApi;\n readonly files: FilesApi;\n readonly workers: WorkersApi;\n readonly baseUrl: string;\n private readonly apiKey?: string;\n\n constructor(config: OctavusClientConfig) {\n this.baseUrl = config.baseUrl.replace(/\\/$/, '');\n this.apiKey = config.apiKey;\n\n const apiConfig: ApiClientConfig = {\n baseUrl: this.baseUrl,\n getHeaders: () => this.getHeaders(),\n };\n\n this.agents = new AgentsApi(apiConfig);\n this.agentSessions = new AgentSessionsApi(apiConfig);\n this.files = new FilesApi(apiConfig);\n this.workers = new WorkersApi(apiConfig);\n }\n\n getHeaders(): Record<string, string> {\n const headers: Record<string, string> = {\n 'Content-Type': 'application/json',\n };\n\n if (this.apiKey) {\n headers.Authorization = `Bearer ${this.apiKey}`;\n }\n\n return headers;\n }\n}\n","/**\n * Base class for agent-managed resources.\n * Extend this class to define how each resource should be persisted when the agent updates it.\n */\nexport abstract class Resource {\n /** The resource name as defined in the agent protocol */\n abstract readonly name: string;\n\n /** Called when the agent updates this resource */\n abstract onUpdate(value: unknown): Promise<void> | void;\n}\n","export { OctavusClient, type OctavusClientConfig } from '@/client.js';\nexport { AgentsApi } from '@/agents.js';\nexport {\n AgentSessionsApi,\n type SessionState,\n type UISessionState,\n type ExpiredSessionState,\n type RestoreSessionResult,\n type SessionStatus,\n type SessionAttachOptions,\n} from '@/agent-sessions.js';\nexport {\n FilesApi,\n type FileUploadRequest,\n type FileUploadInfo,\n type UploadUrlsResponse,\n} from '@/files.js';\nexport {\n AgentSession,\n toSSEStream,\n type SessionConfig,\n type TriggerOptions,\n type SessionRequest,\n type TriggerRequest,\n type ContinueRequest,\n type StopMessage,\n type SocketMessage,\n type SocketMessageHandlers,\n} from '@/session.js';\nexport {\n WorkersApi,\n type WorkerStartRequest,\n type WorkerContinueRequest,\n type WorkerRequest,\n type WorkerExecuteOptions,\n} from '@/workers.js';\nexport { Resource } from '@/resource.js';\nexport { ApiError } from '@/api-error.js';\n\n// Agent types (read-only - use @octavus/cli for agent management)\nexport type {\n AgentFormat,\n AgentSettings,\n AgentPrompt,\n Agent,\n AgentDefinition,\n} from '@/agent-types.js';\n\nexport type * from '@octavus/core';\nexport {\n // Error classes\n AppError,\n NotFoundError,\n ValidationError,\n ConflictError,\n ForbiddenError,\n OctavusError,\n // Error type guards\n isRateLimitError,\n isAuthenticationError,\n isProviderError,\n isToolError,\n isRetryableError,\n isValidationError,\n // Error event helpers\n createErrorEvent,\n errorToStreamEvent,\n createInternalErrorEvent,\n createApiErrorEvent,\n // Utilities\n generateId,\n isAbortError,\n // Thread helpers\n MAIN_THREAD,\n resolveThread,\n isMainThread,\n threadForPart,\n isOtherThread,\n // Type guards\n isFileReference,\n isFileReferenceArray,\n // Safe parse helpers\n safeParseStreamEvent,\n safeParseUIMessage,\n safeParseUIMessages,\n // Skills\n OCTAVUS_SKILL_TOOLS,\n isOctavusSkillTool,\n getSkillSlugFromToolCall,\n} from '@octavus/core';\n"],"mappings":"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","names":["z","z","createInternalErrorEvent","createInternalErrorEvent","z","z","z","createInternalErrorEvent","createApiErrorEvent","isAbortError","safeParseStreamEvent"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@octavus/server-sdk",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.3.0",
|
|
4
4
|
"description": "Server SDK for integrating Octavus agents",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "Octavus AI <dev@octavus.ai>",
|
|
@@ -40,7 +40,7 @@
|
|
|
40
40
|
},
|
|
41
41
|
"dependencies": {
|
|
42
42
|
"zod": "^4.1.13",
|
|
43
|
-
"@octavus/core": "^2.
|
|
43
|
+
"@octavus/core": "^2.3.0"
|
|
44
44
|
},
|
|
45
45
|
"devDependencies": {
|
|
46
46
|
"tsup": "^8.3.5",
|