@camelai/run 0.0.0 → 0.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +62 -1
- package/dist/clients/agents.d.ts +265 -0
- package/dist/clients/agents.js +283 -0
- package/dist/clients/ai-sdk.d.ts +137 -0
- package/dist/clients/ai-sdk.js +461 -0
- package/dist/clients/chat.d.ts +237 -0
- package/dist/clients/chat.js +633 -0
- package/dist/clients/handler.d.ts +116 -0
- package/dist/clients/handler.js +513 -0
- package/dist/clients/markdown.d.ts +72 -0
- package/dist/clients/markdown.js +385 -0
- package/dist/clients/mcp.d.ts +13 -0
- package/dist/clients/mcp.js +38 -0
- package/dist/clients/node.d.ts +21 -0
- package/dist/clients/node.js +76 -0
- package/dist/clients/server.d.ts +83 -0
- package/dist/clients/server.js +187 -0
- package/dist/clients/testing.d.ts +60 -0
- package/dist/clients/testing.js +53 -0
- package/dist/clients/types.d.ts +264 -0
- package/dist/clients/types.js +6 -0
- package/dist/clients/typescript.d.ts +1161 -0
- package/dist/clients/typescript.js +1035 -0
- package/dist/clients/watch.d.ts +90 -0
- package/dist/clients/watch.js +482 -0
- package/dist/shared/client-protocol.d.ts +106 -0
- package/dist/shared/client-protocol.js +9 -0
- package/package.json +78 -1
|
@@ -0,0 +1,1161 @@
|
|
|
1
|
+
import type { AgentEvent, Message, PresentedFile, ThinkingLevel } from "./types.ts";
|
|
2
|
+
import type { Run } from "./agents.ts";
|
|
3
|
+
import { Type, type TSchema, type Static } from "typebox";
|
|
4
|
+
import { type RequestMethod, type SessionCredentials, type SessionState } from "../shared/client-protocol.ts";
|
|
5
|
+
export { Type as schema };
|
|
6
|
+
export type { SessionCredentials, SessionState };
|
|
7
|
+
export type * from "./types.ts";
|
|
8
|
+
/**
|
|
9
|
+
* Who a tool call is for, as the runtime says: from its signed identity token when the tools are
|
|
10
|
+
* served over HTTP (`serveTools`), or from the call itself when they are attached to the agent.
|
|
11
|
+
* Authorize as `user`, within `tenant` and `context`.
|
|
12
|
+
*/
|
|
13
|
+
export interface RuntimeIdentity {
|
|
14
|
+
/** Who is acting: the turn's actor (a prompt's `actor`, or its `from.id`), else the agent's subject. */
|
|
15
|
+
user: string;
|
|
16
|
+
/** Whom the agent acts for, as its creator set it (`createAgent({ subject })`); the agent's id if none. */
|
|
17
|
+
subject: string;
|
|
18
|
+
/** Who is acting in this turn, if the prompt named someone. */
|
|
19
|
+
actor?: string;
|
|
20
|
+
/** The runtime tenant that owns the agent. */
|
|
21
|
+
tenant: string;
|
|
22
|
+
agent: string;
|
|
23
|
+
definition?: string;
|
|
24
|
+
/** Claims the agent's creator attached (`createAgent({ context })`), e.g. `{ org, workspace }`. */
|
|
25
|
+
context: Record<string, unknown>;
|
|
26
|
+
/** Where the turn came from, e.g. `{ channel, conversationId, sender }` for a channel message. */
|
|
27
|
+
origin?: Record<string, unknown>;
|
|
28
|
+
/** The call was approved by a person: which input, who (their ids), and when. */
|
|
29
|
+
approval?: {
|
|
30
|
+
input: string;
|
|
31
|
+
by: Record<string, unknown>;
|
|
32
|
+
at: number;
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
/** A runtime identity from its claims (a verified token's payload, or an attached call's `_meta`). */
|
|
36
|
+
export declare function identityFromClaims(claims: Record<string, any>): RuntimeIdentity;
|
|
37
|
+
export interface ToolContext {
|
|
38
|
+
signal: AbortSignal;
|
|
39
|
+
/**
|
|
40
|
+
* The same for every attempt at this call (a retry after a lost connection, a call run again once the
|
|
41
|
+
* user answered): key your side effects by it, so a call that runs twice acts once.
|
|
42
|
+
*/
|
|
43
|
+
idempotencyKey: string;
|
|
44
|
+
/** This attempt's id (a JSON-RPC id): a new one each attempt, so never a key for side effects. */
|
|
45
|
+
callId: string;
|
|
46
|
+
/** The model's tool call this is (or, from code, the code's call). */
|
|
47
|
+
toolCallId?: string;
|
|
48
|
+
/**
|
|
49
|
+
* Report progress: people watching see it, and each report restarts the tool's timeout (`timeoutMs`),
|
|
50
|
+
* so a long call that keeps reporting is not cut off. A message, or how far it is (`progress` of `total`).
|
|
51
|
+
*/
|
|
52
|
+
progress(update: string | {
|
|
53
|
+
progress: number;
|
|
54
|
+
total?: number;
|
|
55
|
+
message?: string;
|
|
56
|
+
}): void;
|
|
57
|
+
/** Set by the runtime, e.g. `{ channel, conversationId, sender }` for a turn a channel message started. */
|
|
58
|
+
origin?: Record<string, unknown>;
|
|
59
|
+
/** Who the call is for: always set by `serveTools`; set for attached tools by runtimes that send it. */
|
|
60
|
+
identity?: RuntimeIdentity;
|
|
61
|
+
/**
|
|
62
|
+
* Ask the user, and get their answer. The call ends here and the agent's turn waits, for days if need
|
|
63
|
+
* be; once they answer, the runtime calls the tool again with the same arguments, and this returns
|
|
64
|
+
* the answer. So everything before an ask runs again on that call: ask first, act after.
|
|
65
|
+
* `confirm`: whether they said yes. `ask`: what they filled in (a flat object schema), or undefined
|
|
66
|
+
* if they declined. `requireUrl`: whether they say they have done what the https page asks.
|
|
67
|
+
*/
|
|
68
|
+
confirm(message: string): Promise<boolean>;
|
|
69
|
+
ask<T extends Record<string, unknown> = Record<string, unknown>>(message: string, schema: Record<string, unknown>): Promise<T | undefined>;
|
|
70
|
+
requireUrl(url: string, message: string): Promise<boolean>;
|
|
71
|
+
}
|
|
72
|
+
/** Thrown by a ToolContext's asks: the call answers MCP's `input_required`, and runs again once the user answers. */
|
|
73
|
+
export declare class InputRequired extends Error {
|
|
74
|
+
readonly inputRequests: Record<string, {
|
|
75
|
+
method: string;
|
|
76
|
+
params: Record<string, unknown>;
|
|
77
|
+
}>;
|
|
78
|
+
/** The answers so far, which the runtime hands back on the next call (MCP's `requestState`). */
|
|
79
|
+
readonly requestState?: string;
|
|
80
|
+
constructor(inputRequests: InputRequired["inputRequests"], requestState?: string);
|
|
81
|
+
}
|
|
82
|
+
export interface Tool<T = any> {
|
|
83
|
+
description: string;
|
|
84
|
+
/**
|
|
85
|
+
* How long one call may go without an answer before the runtime gives up on it (1 s to 20 minutes;
|
|
86
|
+
* default 15 s).
|
|
87
|
+
* Each `context.progress()` restarts it. A call cut off is an error the model sees; it may still finish here.
|
|
88
|
+
*/
|
|
89
|
+
timeoutMs?: number;
|
|
90
|
+
resultFormat?: "json" | "content";
|
|
91
|
+
exposure?: "direct" | "codemode" | "both";
|
|
92
|
+
executionMode?: "sequential" | "parallel";
|
|
93
|
+
input: Record<string, unknown>;
|
|
94
|
+
/** Return any JSON value (`undefined` is sent as null); throw to tell the model the call failed. */
|
|
95
|
+
execute: (args: T, context: ToolContext) => unknown | Promise<unknown>;
|
|
96
|
+
/**
|
|
97
|
+
* Ask the user to approve each call before it runs (or only the calls this says need it). The runtime
|
|
98
|
+
* shows them the real call; the tool is declared to the model directly, as code cannot wait for a person.
|
|
99
|
+
*/
|
|
100
|
+
needsApproval?: boolean | ((args: T, context: ToolContext) => boolean | Promise<boolean>);
|
|
101
|
+
}
|
|
102
|
+
/** Infer callback arguments from the schema; no manually duplicated argument type. */
|
|
103
|
+
export declare function tool<S extends TSchema>(definition: Omit<Tool<Static<S>>, "input"> & {
|
|
104
|
+
input: S;
|
|
105
|
+
}): Tool<Static<S>>;
|
|
106
|
+
export type Tools = Record<string, Tool>;
|
|
107
|
+
/** A tool as an MCP server lists it (`tools/list`). Runtime options ride in `_meta` under "agent-runtime/". */
|
|
108
|
+
export interface McpTool {
|
|
109
|
+
name: string;
|
|
110
|
+
title?: string;
|
|
111
|
+
description?: string;
|
|
112
|
+
inputSchema: Record<string, unknown>;
|
|
113
|
+
annotations?: Record<string, unknown>;
|
|
114
|
+
_metadata?: Record<string, string>;
|
|
115
|
+
}
|
|
116
|
+
/** An MCP `tools/call` result: complete, or (MCP's multi round-trip requests) asking for input to retry with. */
|
|
117
|
+
export type CallToolResult = {
|
|
118
|
+
content: Array<Record<string, unknown>>;
|
|
119
|
+
structuredContent?: Record<string, unknown>;
|
|
120
|
+
isError?: boolean;
|
|
121
|
+
resultType?: "complete";
|
|
122
|
+
} | {
|
|
123
|
+
resultType: "input_required";
|
|
124
|
+
inputRequests?: Record<string, {
|
|
125
|
+
method: string;
|
|
126
|
+
params?: Record<string, unknown>;
|
|
127
|
+
}>;
|
|
128
|
+
requestState?: string;
|
|
129
|
+
content?: never;
|
|
130
|
+
};
|
|
131
|
+
/**
|
|
132
|
+
* The MCP server an application attaches to its agent: the SDK relays the runtime's
|
|
133
|
+
* `tools/list` and `tools/call` to it over the agent's connection. Throw from `callTool`
|
|
134
|
+
* only when the call could not be answered; a tool's own failure is an `isError` result.
|
|
135
|
+
*/
|
|
136
|
+
export interface ToolServer {
|
|
137
|
+
listTools(): McpTool[] | Promise<McpTool[]>;
|
|
138
|
+
callTool(name: string, args: Record<string, unknown>, context: ToolContext): Promise<CallToolResult>;
|
|
139
|
+
}
|
|
140
|
+
/**
|
|
141
|
+
* A call's context from its params: ids, origin, and the identity the runtime sent in `_meta` (or
|
|
142
|
+
* `identity`, from a verified token); its asks answer from the retry's `inputResponses`, by position.
|
|
143
|
+
*/
|
|
144
|
+
export declare function toolContext(params: Record<string, any>, fallbackId: string, signal: AbortSignal, identity?: RuntimeIdentity, notify?: (message: Record<string, unknown>) => void): ToolContext;
|
|
145
|
+
/**
|
|
146
|
+
* Answer one MCP JSON-RPC request as a tool server: initialize, ping, tools/list and tools/call.
|
|
147
|
+
* Both an attached server (answering over the agent's connection) and `serveTools` (over HTTP) use it.
|
|
148
|
+
*/
|
|
149
|
+
export declare function answerMcp(message: Record<string, any>, server: ToolServer, context: (params: Record<string, any>) => ToolContext, info?: {
|
|
150
|
+
name: string;
|
|
151
|
+
version: string;
|
|
152
|
+
}): Promise<{
|
|
153
|
+
result: unknown;
|
|
154
|
+
} | {
|
|
155
|
+
error: {
|
|
156
|
+
code: number;
|
|
157
|
+
message: string;
|
|
158
|
+
};
|
|
159
|
+
}>;
|
|
160
|
+
/** `tool({...})` definitions as an attached MCP server: JSON results become a text block (and structured content for objects). */
|
|
161
|
+
export declare function toolServer(tools: Tools): ToolServer;
|
|
162
|
+
/** The hosted runtime; `url` points elsewhere (a self-hosted runtime, or http://127.0.0.1:8790 in development). */
|
|
163
|
+
export declare const DEFAULT_URL = "https://agents.camelai.dev";
|
|
164
|
+
export interface RuntimeOptions {
|
|
165
|
+
/** The runtime's origin. Default https://agents.camelai.dev. */
|
|
166
|
+
url?: string;
|
|
167
|
+
apiKey?: string;
|
|
168
|
+
/** Injectable for tests, observability, or an application's HTTP stack. */
|
|
169
|
+
fetch?: typeof globalThis.fetch;
|
|
170
|
+
/** Opens a local file to attach by its path; set by the Node entry (`@camelai/run/node`). */
|
|
171
|
+
openFile?: (path: string) => Promise<Blob>;
|
|
172
|
+
/** How often a request still waiting for its result asks for its status, in case the result's event was lost. Default 30 s. */
|
|
173
|
+
pollMs?: number;
|
|
174
|
+
}
|
|
175
|
+
export interface AgentOptions {
|
|
176
|
+
/** The application's tools, served to the agent as an attached MCP server. */
|
|
177
|
+
tools?: Tools;
|
|
178
|
+
/** Or an MCP server of the application's own (see `clients/mcp.ts` for MCP SDK servers). */
|
|
179
|
+
mcp?: ToolServer;
|
|
180
|
+
/**
|
|
181
|
+
* The agent's events, for display: a run's result is the truth. They are delivered in order, one at a
|
|
182
|
+
* time, apart from the connection (a slow or failing handler never holds up tool calls); an error it
|
|
183
|
+
* throws goes to `onError`. A `message_update` is its delta alone (`assistantMessageEvent`), without the
|
|
184
|
+
* message it updates: fold that from its `message_start` and the deltas since. Where the stream
|
|
185
|
+
* cannot replay (a first connect, or a reconnect after the host's buffer moved on), the first event
|
|
186
|
+
* is a `{ type: "snapshot", turn }` of the running turn to fold from.
|
|
187
|
+
*/
|
|
188
|
+
onEvent?: (event: AgentEvent, requestId?: string) => unknown | Promise<unknown>;
|
|
189
|
+
/**
|
|
190
|
+
* A question, approval or setup step the agent's turn now waits on. Return an answer to give it
|
|
191
|
+
* at once, or nothing to answer later with `agent.answer` (from any process, via connectAgent).
|
|
192
|
+
*/
|
|
193
|
+
onInput?: (input: AgentInput, requestId?: string) => InputAnswer | void | Promise<InputAnswer | void>;
|
|
194
|
+
onConnection?: (connected: boolean) => void;
|
|
195
|
+
onError?: (error: Error) => void;
|
|
196
|
+
/**
|
|
197
|
+
* Whether this client answers the agent's tool calls (its attached MCP server). Default: true. One
|
|
198
|
+
* process is the agent's application at a time; `false` connects to follow the agent and run it only,
|
|
199
|
+
* as any number of processes may (serverless functions, a second service), and answers no tool calls.
|
|
200
|
+
*/
|
|
201
|
+
attach?: boolean;
|
|
202
|
+
/**
|
|
203
|
+
* Replace the process that serves the agent's tools now (it stops serving them, and its onError hears
|
|
204
|
+
* APPLICATION_REPLACED). Without it, connecting while another process serves them fails with APPLICATION_CONNECTED.
|
|
205
|
+
*/
|
|
206
|
+
takeover?: boolean;
|
|
207
|
+
/**
|
|
208
|
+
* Declare this client's tools when they differ from those the agent has, as it connects (default true), so
|
|
209
|
+
* a process restarted with changed tools updates its agent. The declaration applies between the agent's turns.
|
|
210
|
+
*/
|
|
211
|
+
syncTools?: boolean;
|
|
212
|
+
}
|
|
213
|
+
/**
|
|
214
|
+
* Human input a suspended turn waits on (its run ends with `stopped: "input_required"` and these in
|
|
215
|
+
* `inputs`): the model's questions (ask_user), approvals, and a tool's form or URL step.
|
|
216
|
+
*/
|
|
217
|
+
export interface AgentInput {
|
|
218
|
+
id: string;
|
|
219
|
+
agent: string;
|
|
220
|
+
requestId: string;
|
|
221
|
+
toolCallId: string;
|
|
222
|
+
kind: "question" | "approval" | "form" | "url";
|
|
223
|
+
message: string;
|
|
224
|
+
/** What it asks, by `kind`. */
|
|
225
|
+
detail: InputDetail;
|
|
226
|
+
responders: {
|
|
227
|
+
audience?: string[];
|
|
228
|
+
};
|
|
229
|
+
state: "pending" | "answered" | "declined" | "cancelled" | "expired" | "superseded";
|
|
230
|
+
answer?: {
|
|
231
|
+
action: string;
|
|
232
|
+
content?: unknown;
|
|
233
|
+
by: Record<string, unknown>;
|
|
234
|
+
at: number;
|
|
235
|
+
};
|
|
236
|
+
createdAt: number;
|
|
237
|
+
expiresAt: number;
|
|
238
|
+
}
|
|
239
|
+
/** What an input asks: by its `kind`, the fields of one of these. */
|
|
240
|
+
export interface InputDetail {
|
|
241
|
+
/** question: the model's questions (ask_user). */
|
|
242
|
+
questions?: {
|
|
243
|
+
question: string;
|
|
244
|
+
header?: string;
|
|
245
|
+
options: {
|
|
246
|
+
label: string;
|
|
247
|
+
description?: string;
|
|
248
|
+
}[];
|
|
249
|
+
multiSelect: boolean;
|
|
250
|
+
allowOther: boolean;
|
|
251
|
+
}[];
|
|
252
|
+
/** approval: the tool call it waits on, where its tool comes from ("application", "runtime", or a tool source's name), and why it asks. */
|
|
253
|
+
tool?: string;
|
|
254
|
+
source?: string;
|
|
255
|
+
reason?: string;
|
|
256
|
+
/** approval: the call's arguments, as its tool_call event has them; past 4,000 characters of JSON, `argumentsPreview` (their start) instead. */
|
|
257
|
+
arguments?: Record<string, unknown>;
|
|
258
|
+
argumentsPreview?: string;
|
|
259
|
+
argumentsHash?: string;
|
|
260
|
+
/** form: the fields asked for, as a flat JSON Schema. */
|
|
261
|
+
requestedSchema?: Record<string, unknown>;
|
|
262
|
+
/** url: the page to open, and its origin. */
|
|
263
|
+
url?: string;
|
|
264
|
+
origin?: string;
|
|
265
|
+
}
|
|
266
|
+
/** An answer. `content`: for a question, { answers: { "<question>": "<label>" | ["<label>"] | "<own words>" } }; for a form, its fields. `from`/`actor`: who answers, checked against who may. */
|
|
267
|
+
export interface InputAnswer {
|
|
268
|
+
action: "accept" | "decline" | "cancel";
|
|
269
|
+
content?: unknown;
|
|
270
|
+
from?: Sender;
|
|
271
|
+
actor?: string;
|
|
272
|
+
}
|
|
273
|
+
export type { ThinkingLevel };
|
|
274
|
+
export interface CreateAgentOptions extends AgentOptions {
|
|
275
|
+
idempotencyKey?: string;
|
|
276
|
+
/**
|
|
277
|
+
* Make the agent from a definition (GET /v1/definitions): it supplies the model, system
|
|
278
|
+
* prompt, thinking level and tool sources, so leave those out. `tools` (or `mcp`) are added
|
|
279
|
+
* as the agent's attached server.
|
|
280
|
+
*/
|
|
281
|
+
definition?: string;
|
|
282
|
+
/** Agent lifetime in seconds (60 to 366 days), or null to keep it until deleted. Default: until deleted with an `idempotencyKey` of yours, else one day. */
|
|
283
|
+
ttlSeconds?: number | null;
|
|
284
|
+
/** Who the agent acts for (a user id in your app): `sub` in the identity tokens its tool servers get. Set only at creation. */
|
|
285
|
+
subject?: string;
|
|
286
|
+
/** Claims your tool servers need (org, workspace, thread…): `ctx` in its identity tokens. Set only at creation. */
|
|
287
|
+
context?: Record<string, unknown>;
|
|
288
|
+
/** A key scope (PUT /v1/key-scopes/:scope/providers/:provider) whose keys its model calls use first. */
|
|
289
|
+
keyScope?: string;
|
|
290
|
+
/** The most the agent may spend on model calls from now on (USD); PATCH /v1/agents/:id/configuration sets a new one. */
|
|
291
|
+
spendLimit?: {
|
|
292
|
+
usd: number;
|
|
293
|
+
};
|
|
294
|
+
/** Non-secret headers for each of its model calls, e.g. cf-aig-metadata; never auth headers. */
|
|
295
|
+
modelHeaders?: Record<string, string>;
|
|
296
|
+
systemPrompt?: string;
|
|
297
|
+
/** Text the model reads after the system prompt (a definition's, say): per-conversation context. */
|
|
298
|
+
systemPromptAppend?: string;
|
|
299
|
+
/** false: no file tools (read, write, edit, ls, glob, grep) for an application with file tools of its own. */
|
|
300
|
+
fileTools?: boolean;
|
|
301
|
+
name?: string;
|
|
302
|
+
type?: string;
|
|
303
|
+
/**
|
|
304
|
+
* A model from the runtime's catalog as "provider/model-id" (see GET /v1/models),
|
|
305
|
+
* e.g. "anthropic/claude-sonnet-5-5" or "openrouter/openai/gpt-5.2". A full Pi
|
|
306
|
+
* model object is also accepted if its endpoint is trusted by the runtime.
|
|
307
|
+
*/
|
|
308
|
+
model?: string | Record<string, unknown>;
|
|
309
|
+
thinkingLevel?: ThinkingLevel;
|
|
310
|
+
initialMessages?: Message[];
|
|
311
|
+
/** Volumes for the agent's file tools (read, write, edit, ls, glob, grep). Default: its own workspace volume at /workspace. */
|
|
312
|
+
mounts?: Mount[];
|
|
313
|
+
/** Tools the runtime answers itself, for an agent without a definition (one made from a definition has its definition's). */
|
|
314
|
+
builtins?: Builtin[];
|
|
315
|
+
/**
|
|
316
|
+
* A first prompt, sent in the same call once the agent is made (upsertAgent returns its request, or why it was refused).
|
|
317
|
+
* Give it a `requestId`: a retried call with the same key and requestId sends it once.
|
|
318
|
+
*/
|
|
319
|
+
prompt?: {
|
|
320
|
+
text: string;
|
|
321
|
+
requestId?: string;
|
|
322
|
+
actor?: string;
|
|
323
|
+
from?: Sender;
|
|
324
|
+
metadata?: Record<string, string>;
|
|
325
|
+
spendLimit?: {
|
|
326
|
+
usd: number;
|
|
327
|
+
};
|
|
328
|
+
whileRunning?: "queue" | "steer";
|
|
329
|
+
allowDisconnected?: boolean;
|
|
330
|
+
files?: ({
|
|
331
|
+
path: string;
|
|
332
|
+
} | {
|
|
333
|
+
name?: string;
|
|
334
|
+
data: string;
|
|
335
|
+
contentType?: string;
|
|
336
|
+
})[];
|
|
337
|
+
};
|
|
338
|
+
}
|
|
339
|
+
/** A tool the runtime answers itself: web_fetch, web_search, schedule (wake-ups) or ask_user (questions, waiting for the answer). */
|
|
340
|
+
export type Builtin = "web_fetch" | "web_search" | "schedule" | "ask_user";
|
|
341
|
+
/** A volume the agent's file tools see at `path`; `notify` prompts the agent when others change files there. */
|
|
342
|
+
/** How a tool source is authenticated: a stored bearer token, or identity tokens the runtime signs for each request. */
|
|
343
|
+
export type SourceAuth = {
|
|
344
|
+
type: "bearer";
|
|
345
|
+
token: string;
|
|
346
|
+
} | {
|
|
347
|
+
type: "runtime";
|
|
348
|
+
};
|
|
349
|
+
/** Options every tool source takes. `exposure` defaults to both for a source of up to 10 tools, else codemode. */
|
|
350
|
+
interface SourceOptions {
|
|
351
|
+
name: string;
|
|
352
|
+
headers?: Record<string, string>;
|
|
353
|
+
auth?: SourceAuth;
|
|
354
|
+
audience?: string;
|
|
355
|
+
allowTools?: string[];
|
|
356
|
+
denyTools?: string[];
|
|
357
|
+
exposure?: "direct" | "codemode" | "both";
|
|
358
|
+
timeoutMs?: number;
|
|
359
|
+
}
|
|
360
|
+
export interface DefinitionInput {
|
|
361
|
+
name: string;
|
|
362
|
+
model?: string;
|
|
363
|
+
systemPrompt?: string;
|
|
364
|
+
thinkingLevel?: ThinkingLevel;
|
|
365
|
+
limits?: {
|
|
366
|
+
ttlSeconds?: number | null;
|
|
367
|
+
};
|
|
368
|
+
mounts?: unknown[];
|
|
369
|
+
builtins?: Builtin[];
|
|
370
|
+
/** The search providers web_search tries, in order, instead of the runtime's. */
|
|
371
|
+
webSearch?: {
|
|
372
|
+
providers: ("exa" | "brave" | "parallel")[];
|
|
373
|
+
};
|
|
374
|
+
mcpServers?: (SourceOptions & {
|
|
375
|
+
url: string;
|
|
376
|
+
})[];
|
|
377
|
+
openApi?: (SourceOptions & {
|
|
378
|
+
spec?: string | Record<string, unknown>;
|
|
379
|
+
baseUrl?: string;
|
|
380
|
+
})[];
|
|
381
|
+
}
|
|
382
|
+
/** What applying a definition's revision did to one agent; poll a queued one's request for its outcome. */
|
|
383
|
+
export interface ApplyResult {
|
|
384
|
+
agent: string;
|
|
385
|
+
requestId: string;
|
|
386
|
+
status: "updated" | "queued" | "failed";
|
|
387
|
+
error?: string;
|
|
388
|
+
}
|
|
389
|
+
/** A definition as the runtime returns it: credentials are never included. */
|
|
390
|
+
export interface Definition extends Omit<DefinitionInput, "mcpServers" | "openApi"> {
|
|
391
|
+
id: string;
|
|
392
|
+
revision: number;
|
|
393
|
+
createdAt: number;
|
|
394
|
+
updatedAt: number;
|
|
395
|
+
mcpServers?: Record<string, unknown>[];
|
|
396
|
+
openApi?: Record<string, unknown>[];
|
|
397
|
+
applied?: ApplyResult[];
|
|
398
|
+
}
|
|
399
|
+
/** One source of an agent's tools; `excluded` says why the model does not get a tool, when it does not. */
|
|
400
|
+
export interface ToolSource {
|
|
401
|
+
kind: "channel" | "application" | "files" | "builtin" | "mcp" | "openapi";
|
|
402
|
+
name: string;
|
|
403
|
+
/** unlisted: an MCP server the runtime has not listed yet; error: listing it failed. */
|
|
404
|
+
status: "listed" | "unlisted" | "error";
|
|
405
|
+
error?: string;
|
|
406
|
+
listedAt?: number;
|
|
407
|
+
connected?: boolean;
|
|
408
|
+
url?: string;
|
|
409
|
+
exposure?: "direct" | "codemode" | "both";
|
|
410
|
+
tools: {
|
|
411
|
+
name: string;
|
|
412
|
+
description: string;
|
|
413
|
+
exposure?: "direct" | "codemode" | "both";
|
|
414
|
+
executionMode?: "sequential" | "parallel";
|
|
415
|
+
parameters?: Record<string, unknown>;
|
|
416
|
+
excluded?: string;
|
|
417
|
+
}[];
|
|
418
|
+
}
|
|
419
|
+
/**
|
|
420
|
+
* A model on a provider of your own: its id on the server, its context window (compaction keeps requests within it),
|
|
421
|
+
* the most it writes in a reply (default 8,192, or half a smaller window), what it takes in, whether it reasons, its
|
|
422
|
+
* pricing in USD per million tokens (for usage, spend limits and webhooks; none: free), and `compat` switches for a
|
|
423
|
+
* server that differs from OpenAI's.
|
|
424
|
+
*/
|
|
425
|
+
export interface CustomModel {
|
|
426
|
+
id: string;
|
|
427
|
+
contextWindow: number;
|
|
428
|
+
maxOutputTokens?: number;
|
|
429
|
+
input?: ("text" | "image")[];
|
|
430
|
+
reasoning?: boolean;
|
|
431
|
+
pricing?: {
|
|
432
|
+
input: number;
|
|
433
|
+
output: number;
|
|
434
|
+
cacheRead?: number;
|
|
435
|
+
cacheWrite?: number;
|
|
436
|
+
};
|
|
437
|
+
compat?: {
|
|
438
|
+
supportsDeveloperRole?: boolean;
|
|
439
|
+
supportsUsageInStreaming?: boolean;
|
|
440
|
+
supportsFinishReason?: boolean;
|
|
441
|
+
supportsReasoningEffort?: boolean;
|
|
442
|
+
maxTokensField?: "max_tokens" | "max_completion_tokens";
|
|
443
|
+
thinkingFormat?: "openai" | "openrouter" | "deepseek" | "together" | "zai" | "qwen" | "qwen-chat-template";
|
|
444
|
+
};
|
|
445
|
+
}
|
|
446
|
+
/** A provider of your own: a public https server that speaks OpenAI Chat Completions (`POST <baseUrl>/chat/completions`). */
|
|
447
|
+
/** The API a custom provider speaks. */
|
|
448
|
+
export type CustomProviderType = "openai-completions" | "openai-responses" | "anthropic-messages";
|
|
449
|
+
export interface CustomProviderInput {
|
|
450
|
+
type: CustomProviderType;
|
|
451
|
+
baseUrl: string;
|
|
452
|
+
apiKey?: string | null;
|
|
453
|
+
headers?: Record<string, string> | null; /** anthropic-messages: "bearer" sends the key as Authorization: Bearer, not x-api-key. */
|
|
454
|
+
auth?: "x-api-key" | "bearer";
|
|
455
|
+
models: CustomModel[];
|
|
456
|
+
}
|
|
457
|
+
/** A provider as GET /v1/providers lists it; never a key or header value. */
|
|
458
|
+
export interface ProviderSummary {
|
|
459
|
+
id: string;
|
|
460
|
+
kind: "model" | "search" | "fetch";
|
|
461
|
+
models: number;
|
|
462
|
+
apiKey: boolean;
|
|
463
|
+
requires?: string;
|
|
464
|
+
key: {
|
|
465
|
+
provider: string;
|
|
466
|
+
source: "tenant" | "admin" | "platform";
|
|
467
|
+
last4?: string;
|
|
468
|
+
setAt?: number;
|
|
469
|
+
} | null;
|
|
470
|
+
custom?: {
|
|
471
|
+
type: CustomProviderType;
|
|
472
|
+
baseUrl: string;
|
|
473
|
+
auth: "x-api-key" | "bearer";
|
|
474
|
+
headers?: string[];
|
|
475
|
+
models: CustomModel[];
|
|
476
|
+
};
|
|
477
|
+
}
|
|
478
|
+
/** An agent as GET /v1/agents lists it. */
|
|
479
|
+
export interface AgentSummary {
|
|
480
|
+
id: string;
|
|
481
|
+
key: string | null;
|
|
482
|
+
name: string;
|
|
483
|
+
type: string;
|
|
484
|
+
model: string;
|
|
485
|
+
connected: boolean;
|
|
486
|
+
running: boolean;
|
|
487
|
+
expiresAt: number | null;
|
|
488
|
+
resume: {
|
|
489
|
+
failures: number;
|
|
490
|
+
after: number;
|
|
491
|
+
} | null;
|
|
492
|
+
}
|
|
493
|
+
export interface Mount {
|
|
494
|
+
volumeId: string;
|
|
495
|
+
path: string;
|
|
496
|
+
mode: "ro" | "rw";
|
|
497
|
+
subpath?: string;
|
|
498
|
+
notify?: boolean;
|
|
499
|
+
}
|
|
500
|
+
export interface Volume {
|
|
501
|
+
id: string;
|
|
502
|
+
name: string;
|
|
503
|
+
createdAt: number;
|
|
504
|
+
seq?: number;
|
|
505
|
+
files?: number;
|
|
506
|
+
bytes?: number;
|
|
507
|
+
origin?: {
|
|
508
|
+
volume: string;
|
|
509
|
+
snapshot?: string;
|
|
510
|
+
seq: number;
|
|
511
|
+
};
|
|
512
|
+
}
|
|
513
|
+
export interface VolumeFile {
|
|
514
|
+
path: string;
|
|
515
|
+
version: number;
|
|
516
|
+
size: number;
|
|
517
|
+
updatedAt: number;
|
|
518
|
+
by?: string;
|
|
519
|
+
contentType: string;
|
|
520
|
+
}
|
|
521
|
+
export interface VolumeSnapshot {
|
|
522
|
+
id: string;
|
|
523
|
+
volume: string;
|
|
524
|
+
name: string;
|
|
525
|
+
seq: number;
|
|
526
|
+
createdAt: number;
|
|
527
|
+
files: number;
|
|
528
|
+
bytes: number;
|
|
529
|
+
}
|
|
530
|
+
export interface VolumeChanges {
|
|
531
|
+
seq: number;
|
|
532
|
+
changes: {
|
|
533
|
+
seq: number;
|
|
534
|
+
path: string;
|
|
535
|
+
kind: "write" | "delete";
|
|
536
|
+
version?: number;
|
|
537
|
+
size?: number;
|
|
538
|
+
by?: string;
|
|
539
|
+
at: number;
|
|
540
|
+
}[];
|
|
541
|
+
gap?: boolean;
|
|
542
|
+
}
|
|
543
|
+
/** A signed URL for one file: send `method` to `url` with no Authorization header, until `expiresAt`. */
|
|
544
|
+
export interface FileLink {
|
|
545
|
+
url: string;
|
|
546
|
+
method: "GET" | "PUT";
|
|
547
|
+
path: string;
|
|
548
|
+
expiresAt: number;
|
|
549
|
+
maxBytes?: number;
|
|
550
|
+
contentType?: string;
|
|
551
|
+
}
|
|
552
|
+
/** A link's options: `expiresIn` seconds (default 900, at most 86400); for PUT, the largest upload and its content type. */
|
|
553
|
+
export interface LinkOptions {
|
|
554
|
+
method?: "GET" | "PUT";
|
|
555
|
+
expiresIn?: number;
|
|
556
|
+
maxBytes?: number;
|
|
557
|
+
contentType?: string;
|
|
558
|
+
}
|
|
559
|
+
/** A message as the runtime records it: a user message also names its sender (if given), the request that sent it, and the application's `metadata`. */
|
|
560
|
+
export type RecordedMessage = Message & {
|
|
561
|
+
from?: Sender;
|
|
562
|
+
requestId?: string;
|
|
563
|
+
metadata?: Record<string, string>;
|
|
564
|
+
};
|
|
565
|
+
export interface AgentHistory {
|
|
566
|
+
messages: RecordedMessage[];
|
|
567
|
+
}
|
|
568
|
+
/** A page of history: whole turns, oldest first, each message at its index in the agent's history. `next` is the older page's `before` (null at the start). */
|
|
569
|
+
export interface HistoryPage {
|
|
570
|
+
entries: {
|
|
571
|
+
index: number;
|
|
572
|
+
message: RecordedMessage;
|
|
573
|
+
}[];
|
|
574
|
+
next: number | null;
|
|
575
|
+
total: number;
|
|
576
|
+
split?: true;
|
|
577
|
+
}
|
|
578
|
+
/** What a run's model responses used (`run.completed`, `run.failed`); null when it made none on the node that ended it. */
|
|
579
|
+
export interface RunUsage {
|
|
580
|
+
responses: number;
|
|
581
|
+
input: number;
|
|
582
|
+
output: number;
|
|
583
|
+
cacheRead: number;
|
|
584
|
+
cacheWrite: number;
|
|
585
|
+
costUsd: number;
|
|
586
|
+
}
|
|
587
|
+
type RunFacts = {
|
|
588
|
+
agentId: string;
|
|
589
|
+
requestId: string;
|
|
590
|
+
method: "prompt" | "continue" | "resume" | "execute";
|
|
591
|
+
actor?: string;
|
|
592
|
+
metadata?: Record<string, string>;
|
|
593
|
+
};
|
|
594
|
+
/**
|
|
595
|
+
* An event a tenant's webhook endpoint receives (`POST /v1/webhooks {url, events}`), signed per Standard Webhooks.
|
|
596
|
+
* `created` is Unix seconds; dedupe by `id`. Payloads carry ids and key facts: read the rest with the tenant token.
|
|
597
|
+
*/
|
|
598
|
+
export type WebhookEvent = {
|
|
599
|
+
id: string;
|
|
600
|
+
created: number;
|
|
601
|
+
} & ({
|
|
602
|
+
type: "billing.balance.low" | "billing.balance.depleted";
|
|
603
|
+
data: {
|
|
604
|
+
/** Integer micro-USD, including negative balances. */
|
|
605
|
+
balance: number;
|
|
606
|
+
threshold: number;
|
|
607
|
+
previousBalance?: number;
|
|
608
|
+
source: "balance" | "threshold_changed";
|
|
609
|
+
};
|
|
610
|
+
} | {
|
|
611
|
+
type: "run.started";
|
|
612
|
+
data: RunFacts & {
|
|
613
|
+
resumes?: number;
|
|
614
|
+
};
|
|
615
|
+
} | {
|
|
616
|
+
type: "run.completed";
|
|
617
|
+
data: RunFacts & {
|
|
618
|
+
usage: RunUsage | null;
|
|
619
|
+
stopped?: "input_required" | "spend_limit";
|
|
620
|
+
inputIds?: string[];
|
|
621
|
+
replyIndex?: number;
|
|
622
|
+
messageCount?: number;
|
|
623
|
+
steeredInto?: string;
|
|
624
|
+
};
|
|
625
|
+
} | {
|
|
626
|
+
type: "run.failed";
|
|
627
|
+
data: RunFacts & {
|
|
628
|
+
usage: RunUsage | null;
|
|
629
|
+
error: string;
|
|
630
|
+
uncertain?: boolean;
|
|
631
|
+
steeredInto?: string;
|
|
632
|
+
};
|
|
633
|
+
} | {
|
|
634
|
+
type: "input.requested";
|
|
635
|
+
data: {
|
|
636
|
+
agentId: string;
|
|
637
|
+
requestId: string;
|
|
638
|
+
inputId: string;
|
|
639
|
+
toolCallId: string;
|
|
640
|
+
kind: AgentInput["kind"];
|
|
641
|
+
expiresAt: number;
|
|
642
|
+
};
|
|
643
|
+
} | {
|
|
644
|
+
type: "input.resolved";
|
|
645
|
+
data: {
|
|
646
|
+
agentId: string;
|
|
647
|
+
requestId: string;
|
|
648
|
+
inputId: string;
|
|
649
|
+
state: Exclude<AgentInput["state"], "pending">;
|
|
650
|
+
};
|
|
651
|
+
} | {
|
|
652
|
+
type: "usage.recorded";
|
|
653
|
+
data: {
|
|
654
|
+
agentId: string;
|
|
655
|
+
requestId: string | null;
|
|
656
|
+
subject: string;
|
|
657
|
+
actor: string | null;
|
|
658
|
+
context: Record<string, unknown>;
|
|
659
|
+
keyScope: string | null;
|
|
660
|
+
provider: string;
|
|
661
|
+
model: string;
|
|
662
|
+
kind: "response" | "compaction";
|
|
663
|
+
input: number;
|
|
664
|
+
output: number;
|
|
665
|
+
cacheRead: number;
|
|
666
|
+
cacheWrite: number;
|
|
667
|
+
reasoning?: number;
|
|
668
|
+
cost: {
|
|
669
|
+
usd: number;
|
|
670
|
+
source: "provider" | "catalog";
|
|
671
|
+
};
|
|
672
|
+
at: number;
|
|
673
|
+
};
|
|
674
|
+
});
|
|
675
|
+
/**
|
|
676
|
+
* A file to attach to a message: bytes or a Blob (a File keeps its name and type), `{ name, data,
|
|
677
|
+
* contentType? }`, a local path (Node entry), or `{ path }` for a file already in the agent's mounts.
|
|
678
|
+
* The SDK uploads each to the agent's workspace (uploads/<request>/<name>) before sending the message.
|
|
679
|
+
*/
|
|
680
|
+
export type Attachment = Uint8Array | Blob | string | {
|
|
681
|
+
name?: string;
|
|
682
|
+
data: Uint8Array | Blob;
|
|
683
|
+
contentType?: string;
|
|
684
|
+
} | {
|
|
685
|
+
path: string;
|
|
686
|
+
};
|
|
687
|
+
/** A file in the agent's mounts, at the path the agent sees it. */
|
|
688
|
+
export interface AgentFile {
|
|
689
|
+
path: string;
|
|
690
|
+
version: number;
|
|
691
|
+
size: number;
|
|
692
|
+
updatedAt: number;
|
|
693
|
+
by?: string;
|
|
694
|
+
contentType: string;
|
|
695
|
+
}
|
|
696
|
+
export interface Schedule {
|
|
697
|
+
id: string;
|
|
698
|
+
agent: string;
|
|
699
|
+
text?: string;
|
|
700
|
+
code?: string;
|
|
701
|
+
dueAt: number;
|
|
702
|
+
everySeconds?: number;
|
|
703
|
+
createdAt: number;
|
|
704
|
+
}
|
|
705
|
+
/**
|
|
706
|
+
* `idempotencyKey`: the request's id; sending the same key again returns the same request, never a second one.
|
|
707
|
+
* `signal`: stop waiting (the request goes on; `abort()` stops the agent's turn). `timeoutMs`: the same, after a time.
|
|
708
|
+
*/
|
|
709
|
+
export interface RequestOptions {
|
|
710
|
+
idempotencyKey?: string;
|
|
711
|
+
timeoutMs?: number;
|
|
712
|
+
signal?: AbortSignal;
|
|
713
|
+
}
|
|
714
|
+
/**
|
|
715
|
+
* `allowDisconnected`: run even when no process serves the agent's tools (its calls to them then fail as
|
|
716
|
+
* not_connected). Without it, a run of an agent with application tools and none connected is refused
|
|
717
|
+
* with APPLICATION_NOT_CONNECTED.
|
|
718
|
+
*/
|
|
719
|
+
export interface RunRequestOptions extends RequestOptions {
|
|
720
|
+
allowDisconnected?: boolean;
|
|
721
|
+
}
|
|
722
|
+
/** Who sent a message: `id` is yours and the model may rely on it; the names are the sender's own. */
|
|
723
|
+
export interface Sender {
|
|
724
|
+
id: string;
|
|
725
|
+
name?: string;
|
|
726
|
+
username?: string;
|
|
727
|
+
}
|
|
728
|
+
export declare class AgentError extends Error {
|
|
729
|
+
/** The HTTP status, or 0 for a failure that is not an HTTP response's (a run's, the connection's). */
|
|
730
|
+
status: number;
|
|
731
|
+
requestId?: string;
|
|
732
|
+
/** A stable name for the failure where the runtime gives one, e.g. APPLICATION_NOT_CONNECTED. */
|
|
733
|
+
code?: string;
|
|
734
|
+
/** The runtime could not tell whether the work took effect (a restart cut it short). */
|
|
735
|
+
uncertain?: boolean;
|
|
736
|
+
/** Milliseconds the runtime asked to wait before retrying (its Retry-After), for 429 and 503. */
|
|
737
|
+
retryAfterMs?: number;
|
|
738
|
+
constructor(message: string, status?: number, requestId?: string);
|
|
739
|
+
}
|
|
740
|
+
/** A run that failed (`agent.run` throws it unless `throwOnError: false`): `run` is how it ended, `code` why. */
|
|
741
|
+
export declare class RunError extends AgentError {
|
|
742
|
+
readonly run: Run;
|
|
743
|
+
constructor(run: Run);
|
|
744
|
+
}
|
|
745
|
+
/** What a run produced: its reply, how it stopped, the inputs it waits on and the files it wrote. */
|
|
746
|
+
export interface RunResult {
|
|
747
|
+
/** The final assistant message's text ("" when it said nothing). */
|
|
748
|
+
reply?: string;
|
|
749
|
+
/** The model's error, or null. */
|
|
750
|
+
error: string | null;
|
|
751
|
+
/** Why it stopped early: waiting on human input (`inputs`), or its spend limit. */
|
|
752
|
+
stopped?: "input_required" | "spend_limit";
|
|
753
|
+
inputs?: AgentInput[];
|
|
754
|
+
replyIndex?: number;
|
|
755
|
+
/** Messages in the agent's history after it. */
|
|
756
|
+
messages?: number;
|
|
757
|
+
files?: AgentFile[];
|
|
758
|
+
presented?: PresentedFile[];
|
|
759
|
+
usage?: RunUsage | null;
|
|
760
|
+
/** A stable name for `error`, where the runtime gives one. */
|
|
761
|
+
code?: string;
|
|
762
|
+
/** Tool calls that did not complete (the model was told): timed out, lost, with no application connected, and so on. */
|
|
763
|
+
toolErrors?: ToolError[];
|
|
764
|
+
/** Tool sources (MCP servers, OpenAPI specs) that could not be listed, so the model went without their tools. */
|
|
765
|
+
sourceErrors?: {
|
|
766
|
+
kind: string;
|
|
767
|
+
source: string;
|
|
768
|
+
message: string;
|
|
769
|
+
}[];
|
|
770
|
+
}
|
|
771
|
+
/**
|
|
772
|
+
* A tool call that did not complete. `code`: timeout or connection_lost (with `outcomeUnknown`: it may have
|
|
773
|
+
* taken effect), not_connected (no application was connected to run it: it did not run), source_unavailable, failed.
|
|
774
|
+
*/
|
|
775
|
+
export interface ToolError {
|
|
776
|
+
tool: string;
|
|
777
|
+
toolCallId?: string;
|
|
778
|
+
innerCallId?: string;
|
|
779
|
+
code: "timeout" | "connection_lost" | "not_connected" | "source_unavailable" | "failed";
|
|
780
|
+
outcomeUnknown?: true;
|
|
781
|
+
message: string;
|
|
782
|
+
}
|
|
783
|
+
/**
|
|
784
|
+
* Hosts plain http:// may reach: loopback, and names and addresses only a private network resolves
|
|
785
|
+
* (a Docker Compose service, `*.internal`, `*.local`, 10/8, 172.16/12, 192.168/16), as for a runtime kept private.
|
|
786
|
+
*/
|
|
787
|
+
export declare function privateHost(hostname: string): boolean;
|
|
788
|
+
declare class Transport {
|
|
789
|
+
readonly base: string;
|
|
790
|
+
readonly fetcher: typeof globalThis.fetch;
|
|
791
|
+
constructor(options: RuntimeOptions);
|
|
792
|
+
json(path: string, token: string, method?: string, body?: unknown, retry?: boolean, headers?: Record<string, string>): Promise<any>;
|
|
793
|
+
/**
|
|
794
|
+
* A request with a raw body or response (file contents). It fails once nothing arrives for 30 s
|
|
795
|
+
* (an upload has the runtime's 15 minutes to be sent), so a stalled transfer never hangs its caller.
|
|
796
|
+
*/
|
|
797
|
+
raw(path: string, token: string, init?: {
|
|
798
|
+
method?: string;
|
|
799
|
+
body?: Uint8Array | Blob;
|
|
800
|
+
headers?: Record<string, string>;
|
|
801
|
+
}): Promise<Response>;
|
|
802
|
+
private transfer;
|
|
803
|
+
}
|
|
804
|
+
/** Trusted-backend SDK. Only createAgent needs the operator key. */
|
|
805
|
+
export declare class AgentRuntime {
|
|
806
|
+
readonly options: RuntimeOptions;
|
|
807
|
+
private readonly transport;
|
|
808
|
+
constructor(options?: RuntimeOptions);
|
|
809
|
+
/**
|
|
810
|
+
* The agent for `key`: made if there is none, set to `options` if it differs. Returns its credentials;
|
|
811
|
+
* connect with `connectAgent`. Keyed agents live until they are deleted.
|
|
812
|
+
*/
|
|
813
|
+
upsertAgent(key: string, options: CreateAgentOptions): Promise<{
|
|
814
|
+
session: SessionCredentials;
|
|
815
|
+
reconfigured?: {
|
|
816
|
+
id: string;
|
|
817
|
+
};
|
|
818
|
+
prompt?: {
|
|
819
|
+
id: string;
|
|
820
|
+
state: "running" | "completed";
|
|
821
|
+
[field: string]: unknown;
|
|
822
|
+
} | {
|
|
823
|
+
error: {
|
|
824
|
+
status: number;
|
|
825
|
+
code: string;
|
|
826
|
+
message: string;
|
|
827
|
+
};
|
|
828
|
+
};
|
|
829
|
+
}>;
|
|
830
|
+
createAgent(options: CreateAgentOptions): Promise<AgentClient>;
|
|
831
|
+
connectAgent(session: SessionCredentials, options: AgentOptions): Promise<AgentClient>;
|
|
832
|
+
private operator;
|
|
833
|
+
/**
|
|
834
|
+
* Add or replace a provider of your own: a server that speaks OpenAI Chat Completions, with the models it has. Agents
|
|
835
|
+
* name them `<name>/<model id>`. `apiKey` and `headers` left out keep what is stored; null removes them.
|
|
836
|
+
*/
|
|
837
|
+
setProvider(name: string, config: CustomProviderInput): Promise<ProviderSummary>;
|
|
838
|
+
deleteProvider(name: string): Promise<{
|
|
839
|
+
deleted: true;
|
|
840
|
+
}>;
|
|
841
|
+
/** Every provider: the built-in ones with your keys' status, and your own (`custom`). */
|
|
842
|
+
providers(): Promise<ProviderSummary[]>;
|
|
843
|
+
/** The tenant's agents, each with the key it was made with (null for one made without) and its name. */
|
|
844
|
+
listAgents(): Promise<AgentSummary[]>;
|
|
845
|
+
createVolume(options?: {
|
|
846
|
+
name?: string;
|
|
847
|
+
}): Promise<Volume>;
|
|
848
|
+
listVolumes(): Promise<Volume[]>;
|
|
849
|
+
/** A handle on one volume's files, snapshots and forks. */
|
|
850
|
+
volume(id: string): VolumeHandle;
|
|
851
|
+
/**
|
|
852
|
+
* Definitions: reusable agent configurations with their tool sources (MCP servers, OpenAPI
|
|
853
|
+
* specs, built-ins). Make agents from one with `createAgent({ definition: id })`.
|
|
854
|
+
*/
|
|
855
|
+
createDefinition(input: DefinitionInput): Promise<Definition>;
|
|
856
|
+
/** The definition for `key`, set to `input` whole: made if there is none, else a new revision if `input` changes it. The same key is the same definition. */
|
|
857
|
+
upsertDefinition(key: string, input: DefinitionInput): Promise<Definition>;
|
|
858
|
+
/** Replace the fields given (null removes one); `apply: "all"` also reconfigures its live agents between their turns. */
|
|
859
|
+
updateDefinition(id: string, input: Partial<DefinitionInput> & {
|
|
860
|
+
revision?: number;
|
|
861
|
+
apply?: "all";
|
|
862
|
+
}): Promise<Definition>;
|
|
863
|
+
definition(id: string): Promise<Definition>;
|
|
864
|
+
definitions(): Promise<Definition[]>;
|
|
865
|
+
deleteDefinition(id: string): Promise<{
|
|
866
|
+
deleted: boolean;
|
|
867
|
+
}>;
|
|
868
|
+
mounts(agentId: string): Promise<Mount[]>;
|
|
869
|
+
/** Replace an agent's mounts; an idle agent restarts so its tools describe them. */
|
|
870
|
+
setMounts(agentId: string, mounts: Mount[]): Promise<Mount[]>;
|
|
871
|
+
/**
|
|
872
|
+
* Every source of an agent's tools (its application, file tools, built-ins, MCP servers, OpenAPI
|
|
873
|
+
* specs) and what each offers the model. `schemas` includes input schemas; `refresh` lists MCP servers now.
|
|
874
|
+
*/
|
|
875
|
+
/**
|
|
876
|
+
* A token a browser reads one agent with (`@camelai/run/watch`): mint one per user, after your
|
|
877
|
+
* own access checks. It reads only that agent's events, state, history and inputs (or `scopes`), for
|
|
878
|
+
* `ttlSeconds` (default 900, 5 to 3600).
|
|
879
|
+
*/
|
|
880
|
+
browserToken(agentId: string, options?: {
|
|
881
|
+
ttlSeconds?: number;
|
|
882
|
+
scopes?: ("events" | "state" | "history" | "inputs")[];
|
|
883
|
+
events?: string[];
|
|
884
|
+
redact?: "usage.cost"[];
|
|
885
|
+
subject?: string;
|
|
886
|
+
}): Promise<{
|
|
887
|
+
token: string;
|
|
888
|
+
expiresAt: number;
|
|
889
|
+
agentId: string;
|
|
890
|
+
url?: string;
|
|
891
|
+
}>;
|
|
892
|
+
/** Who the API key is: `tenant` is your tenant's id, which serveTools and verifyRuntimeToken take. */
|
|
893
|
+
/** Who the API key is (`tenant`), and `defaultModel`, the model an agent gets when it names none. */
|
|
894
|
+
me(): Promise<{
|
|
895
|
+
tenant: string;
|
|
896
|
+
via: string;
|
|
897
|
+
login?: string;
|
|
898
|
+
defaultModel: string;
|
|
899
|
+
}>;
|
|
900
|
+
/** Inputs waiting on someone across all the tenant's agents (`pending` ones, say), newest first. */
|
|
901
|
+
inbox(state?: AgentInput["state"]): Promise<AgentInput[]>;
|
|
902
|
+
toolSources(agentId: string, options?: {
|
|
903
|
+
schemas?: boolean;
|
|
904
|
+
refresh?: boolean;
|
|
905
|
+
}): Promise<ToolSource[]>;
|
|
906
|
+
}
|
|
907
|
+
/** Files are versioned: pass `version` to write or remove only if nobody changed the file since (0: must not exist). */
|
|
908
|
+
export declare class VolumeHandle {
|
|
909
|
+
readonly id: string;
|
|
910
|
+
private readonly transport;
|
|
911
|
+
private readonly token;
|
|
912
|
+
constructor(transport: Transport, token: string, id: string);
|
|
913
|
+
private path;
|
|
914
|
+
private file;
|
|
915
|
+
info(): Promise<Volume>;
|
|
916
|
+
delete(): Promise<any>;
|
|
917
|
+
snapshot(options?: {
|
|
918
|
+
name?: string;
|
|
919
|
+
}): Promise<VolumeSnapshot>;
|
|
920
|
+
snapshots(): Promise<VolumeSnapshot[]>;
|
|
921
|
+
deleteSnapshot(id: string): Promise<any>;
|
|
922
|
+
/** A new volume with this one's files (or a snapshot's); only metadata is copied. */
|
|
923
|
+
fork(options?: {
|
|
924
|
+
name?: string;
|
|
925
|
+
snapshot?: string;
|
|
926
|
+
}): Promise<Volume>;
|
|
927
|
+
changes(since?: number): Promise<VolumeChanges>;
|
|
928
|
+
list(options?: {
|
|
929
|
+
prefix?: string;
|
|
930
|
+
glob?: string;
|
|
931
|
+
after?: string;
|
|
932
|
+
limit?: number;
|
|
933
|
+
}): Promise<{
|
|
934
|
+
files: VolumeFile[];
|
|
935
|
+
next?: string;
|
|
936
|
+
}>;
|
|
937
|
+
/** Without `contentType`, the runtime sniffs it from the file's first bytes and name. */
|
|
938
|
+
write(path: string, data: string | Uint8Array, options?: {
|
|
939
|
+
version?: number;
|
|
940
|
+
contentType?: string;
|
|
941
|
+
}): Promise<VolumeFile>;
|
|
942
|
+
/** A file's bytes, or `range` of them ([start, end) in bytes). */
|
|
943
|
+
read(path: string, options?: {
|
|
944
|
+
range?: [number, number?];
|
|
945
|
+
}): Promise<{
|
|
946
|
+
data: Uint8Array;
|
|
947
|
+
version: number;
|
|
948
|
+
contentType: string;
|
|
949
|
+
}>;
|
|
950
|
+
readText(path: string): Promise<string>;
|
|
951
|
+
/** A signed URL to download (GET) or upload (PUT) one file without a token. */
|
|
952
|
+
link(path: string, options?: LinkOptions): Promise<FileLink>;
|
|
953
|
+
remove(path: string, options?: {
|
|
954
|
+
version?: number;
|
|
955
|
+
}): Promise<any>;
|
|
956
|
+
}
|
|
957
|
+
declare const INSPECT: unique symbol;
|
|
958
|
+
/**
|
|
959
|
+
* The agent's files, at the paths it sees them (`/workspace/report.pdf`), with the agent's own
|
|
960
|
+
* token: what it wrote during a run (a run's outcome lists `files`), and links to hand them on.
|
|
961
|
+
*/
|
|
962
|
+
export declare class AgentFiles {
|
|
963
|
+
private readonly transport;
|
|
964
|
+
private readonly token;
|
|
965
|
+
private readonly base;
|
|
966
|
+
constructor(transport: Transport, token: string, base: string);
|
|
967
|
+
/** Files under `path` (default: the first mount), in path order, a page at a time. */
|
|
968
|
+
list(options?: {
|
|
969
|
+
path?: string;
|
|
970
|
+
glob?: string;
|
|
971
|
+
after?: string;
|
|
972
|
+
limit?: number;
|
|
973
|
+
}): Promise<{
|
|
974
|
+
files: AgentFile[];
|
|
975
|
+
next?: string;
|
|
976
|
+
}>;
|
|
977
|
+
download(path: string): Promise<{
|
|
978
|
+
data: Uint8Array;
|
|
979
|
+
contentType: string;
|
|
980
|
+
version: number;
|
|
981
|
+
}>;
|
|
982
|
+
/** Write a file into a writable mount; without `contentType` the runtime sniffs it. */
|
|
983
|
+
upload(path: string, data: Uint8Array | Blob | string, options?: {
|
|
984
|
+
contentType?: string;
|
|
985
|
+
}): Promise<AgentFile>;
|
|
986
|
+
/** A signed URL to download (GET) or upload (PUT) one file without a token, e.g. for a browser or another service. */
|
|
987
|
+
link(path: string, options?: LinkOptions): Promise<FileLink>;
|
|
988
|
+
}
|
|
989
|
+
export declare class AgentClient {
|
|
990
|
+
/** The agent's id (client_…): safe to log and to store. */
|
|
991
|
+
readonly id: string;
|
|
992
|
+
/** The agent's id and its token: keep the token secret (it is left out of logs and JSON). */
|
|
993
|
+
readonly session: SessionCredentials;
|
|
994
|
+
readonly tools: Tools;
|
|
995
|
+
private server;
|
|
996
|
+
private readonly transport;
|
|
997
|
+
/** The last event taken from the stream: a reconnect resumes after it (a new client starts from a snapshot). */
|
|
998
|
+
private cursor;
|
|
999
|
+
private readonly options;
|
|
1000
|
+
private readonly openFile?;
|
|
1001
|
+
private readonly pollMs;
|
|
1002
|
+
/** The agent's files: list, download, upload and link. */
|
|
1003
|
+
readonly files: AgentFiles;
|
|
1004
|
+
private readonly pending;
|
|
1005
|
+
/** Tool calls running, by JSON-RPC id, so the runtime can cancel them. */
|
|
1006
|
+
private readonly active;
|
|
1007
|
+
/** The event stream's connection, named in the MCP messages this client sends back. */
|
|
1008
|
+
private connection?;
|
|
1009
|
+
private stream?;
|
|
1010
|
+
private loop?;
|
|
1011
|
+
private closed;
|
|
1012
|
+
private fatal?;
|
|
1013
|
+
private ready;
|
|
1014
|
+
/** onEvent's queue: events wait here, in order, so the stream never waits on the application. */
|
|
1015
|
+
private dispatching;
|
|
1016
|
+
private queued;
|
|
1017
|
+
private dropped;
|
|
1018
|
+
private readonly listeners;
|
|
1019
|
+
private attaching;
|
|
1020
|
+
/** The stream was cut on purpose, to reconnect in another mode: not an error to report. */
|
|
1021
|
+
private switching;
|
|
1022
|
+
constructor(runtime: RuntimeOptions, session: SessionCredentials, options: AgentOptions);
|
|
1023
|
+
private path;
|
|
1024
|
+
private http;
|
|
1025
|
+
private report;
|
|
1026
|
+
connect(): Promise<void>;
|
|
1027
|
+
private events;
|
|
1028
|
+
/** Rename/regroup this agent without changing its conversation or tools. */
|
|
1029
|
+
setMetadata(metadata: {
|
|
1030
|
+
name: string;
|
|
1031
|
+
type: string;
|
|
1032
|
+
}): Promise<any>;
|
|
1033
|
+
/** Hand an event to the listeners, and queue it for onEvent: the stream goes on without waiting for either. */
|
|
1034
|
+
private emit;
|
|
1035
|
+
/** @internal Hear every event as it arrives (synchronously, before onEvent); returns the unsubscribe. */
|
|
1036
|
+
listen(listener: (event: AgentEvent, requestId?: string) => void): () => void;
|
|
1037
|
+
/** Resolves once onEvent has handled every event received so far. */
|
|
1038
|
+
drained(): Promise<void>;
|
|
1039
|
+
private receive;
|
|
1040
|
+
private settle;
|
|
1041
|
+
/**
|
|
1042
|
+
* A request's result arrives as an event; a reconnect also settles from /state. As a last resort,
|
|
1043
|
+
* ask for its status now and then, so an event lost on the way can never strand the caller.
|
|
1044
|
+
*/
|
|
1045
|
+
private outcome;
|
|
1046
|
+
private sync;
|
|
1047
|
+
/**
|
|
1048
|
+
* Answer the runtime's JSON-RPC messages as the agent's attached MCP server: initialize,
|
|
1049
|
+
* ping, tools/list and tools/call, and cancellation. The runtime runs a call once; a call
|
|
1050
|
+
* whose answer is lost with the connection ends for the agent as "outcome unknown".
|
|
1051
|
+
*/
|
|
1052
|
+
private mcp;
|
|
1053
|
+
/**
|
|
1054
|
+
* Send a request and wait for its outcome, however long the run takes: there is no timeout unless
|
|
1055
|
+
* `timeoutMs` or `signal` says so, and either only stops the wait (the request goes on).
|
|
1056
|
+
*/
|
|
1057
|
+
request(method: RequestMethod, params?: Record<string, unknown>, options?: RequestOptions): Promise<any>;
|
|
1058
|
+
/**
|
|
1059
|
+
* Wait for request `id` to settle, until `timeoutMs` or `signal` says to stop waiting. Calls waiting on the same
|
|
1060
|
+
* request share its settlement (the same key sent again joins the run), and each stops waiting on its own.
|
|
1061
|
+
*/
|
|
1062
|
+
private waiter;
|
|
1063
|
+
/** Wait for a request already sent (by this process or another) to settle. This never submits or re-executes work. */
|
|
1064
|
+
waitForRequest(id: string, options?: {
|
|
1065
|
+
timeoutMs?: number;
|
|
1066
|
+
signal?: AbortSignal;
|
|
1067
|
+
}): Promise<any>;
|
|
1068
|
+
/**
|
|
1069
|
+
* `from` says who sent the message: the model sees it in a block only the runtime can write, and
|
|
1070
|
+
* `from.id` is the turn's actor. `actor` names someone else acting (`act` in identity tokens) without telling the model.
|
|
1071
|
+
* `metadata` is the application's own key-value data about the message (at most 16 string values): the
|
|
1072
|
+
* stored message and its request carry it, with the request's id, in history, events and webhooks; the model never sees it.
|
|
1073
|
+
* `whileRunning: "steer"` hands the message to a running turn, and resolves with that turn's outcome. `spendLimit` is this run's own
|
|
1074
|
+
* budget: it ends before its next model request once it has spent that; the agent's spendLimit is unchanged.
|
|
1075
|
+
*/
|
|
1076
|
+
prompt(text: string, options?: RunRequestOptions & {
|
|
1077
|
+
files?: Attachment[];
|
|
1078
|
+
actor?: string;
|
|
1079
|
+
from?: Sender;
|
|
1080
|
+
metadata?: Record<string, string>;
|
|
1081
|
+
whileRunning?: "queue" | "steer";
|
|
1082
|
+
spendLimit?: {
|
|
1083
|
+
usd: number;
|
|
1084
|
+
};
|
|
1085
|
+
}): Promise<any>;
|
|
1086
|
+
/**
|
|
1087
|
+
* Send a message with its files: each is uploaded to the agent's workspace under the request's
|
|
1088
|
+
* id first, then attached by path.
|
|
1089
|
+
*/
|
|
1090
|
+
private message;
|
|
1091
|
+
private attach;
|
|
1092
|
+
history(): Promise<AgentHistory>;
|
|
1093
|
+
/**
|
|
1094
|
+
* The page of whole turns ending before `before` (default: the newest message, the running turn's
|
|
1095
|
+
* included), with at least `limit` messages (default 50) where there are that many. It reads only
|
|
1096
|
+
* that page, however long the history.
|
|
1097
|
+
*/
|
|
1098
|
+
historyPage(options?: {
|
|
1099
|
+
before?: number;
|
|
1100
|
+
limit?: number;
|
|
1101
|
+
}): Promise<HistoryPage>;
|
|
1102
|
+
continue(options?: RunRequestOptions & {
|
|
1103
|
+
actor?: string;
|
|
1104
|
+
}): Promise<any>;
|
|
1105
|
+
/** The legacy steer request: a message held for the running turn. New code: `prompt(text, { whileRunning: "steer" })`. */
|
|
1106
|
+
steer(text: string, options?: {
|
|
1107
|
+
from?: Sender;
|
|
1108
|
+
files?: Attachment[];
|
|
1109
|
+
metadata?: Record<string, string>;
|
|
1110
|
+
}): Promise<any>;
|
|
1111
|
+
/** Change the prompt, thinking level, tools, or model ("provider/model-id") between runs. */
|
|
1112
|
+
configure(options: {
|
|
1113
|
+
systemPrompt?: string;
|
|
1114
|
+
thinkingLevel?: ThinkingLevel;
|
|
1115
|
+
tools?: Tools;
|
|
1116
|
+
mcp?: ToolServer;
|
|
1117
|
+
model?: string;
|
|
1118
|
+
}): Promise<any>;
|
|
1119
|
+
/** Declare this client's tools when they differ from what the agent has (its `toolsHash`). */
|
|
1120
|
+
private syncTools;
|
|
1121
|
+
/** Connect again, attached (answering tool calls) or not. */
|
|
1122
|
+
private reconnect;
|
|
1123
|
+
execute(code: string, options?: RunRequestOptions & {
|
|
1124
|
+
timeoutMs?: number;
|
|
1125
|
+
executionTimeoutMs?: number;
|
|
1126
|
+
actor?: string;
|
|
1127
|
+
}): Promise<any>;
|
|
1128
|
+
/**
|
|
1129
|
+
* Wake this agent later: with `text` it gets a prompt, with `code` it runs sandboxed
|
|
1130
|
+
* code against your tools. `everySeconds` (at least 60) repeats it.
|
|
1131
|
+
*/
|
|
1132
|
+
schedule(input: {
|
|
1133
|
+
text?: string;
|
|
1134
|
+
code?: string;
|
|
1135
|
+
at?: string | Date;
|
|
1136
|
+
inSeconds?: number;
|
|
1137
|
+
everySeconds?: number;
|
|
1138
|
+
}): Promise<Schedule>;
|
|
1139
|
+
schedules(): Promise<Schedule[]>;
|
|
1140
|
+
unschedule(id: string): Promise<any>;
|
|
1141
|
+
status(): Promise<any>;
|
|
1142
|
+
abort(): Promise<any>;
|
|
1143
|
+
requestStatus(id: string): Promise<any>;
|
|
1144
|
+
/** Answer an input the agent waits on. `request` is the run resuming its turn, once its last input is answered. */
|
|
1145
|
+
answer(inputId: string, answer: InputAnswer): Promise<{
|
|
1146
|
+
input: AgentInput;
|
|
1147
|
+
request: any | null;
|
|
1148
|
+
}>;
|
|
1149
|
+
/** The agent's inputs, newest first: `pending` ones, say. */
|
|
1150
|
+
inputs(state?: AgentInput["state"]): Promise<AgentInput[]>;
|
|
1151
|
+
outcomes(): Promise<SessionState>;
|
|
1152
|
+
toJSON(): {
|
|
1153
|
+
id: string;
|
|
1154
|
+
};
|
|
1155
|
+
[INSPECT](): string;
|
|
1156
|
+
close(): Promise<void>;
|
|
1157
|
+
destroy(): Promise<void>;
|
|
1158
|
+
[Symbol.asyncDispose](): Promise<void>;
|
|
1159
|
+
}
|
|
1160
|
+
export { Agents, Agent } from "./agents.ts";
|
|
1161
|
+
export type { AgentsOptions, AgentConfig, Run, RunFailure, RunInput, RunOptions, RunStream, StreamPart, InputValue, AnswerOptions } from "./agents.ts";
|