withruntime 0.18.0 → 0.21.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/COMPATIBILITY.md +32 -1
- package/README.md +19 -0
- package/README.src.md +19 -0
- package/dist/agents/index.d.ts +11 -0
- package/dist/agents/index.js +12 -0
- package/dist/agents-cli.d.ts +10 -0
- package/dist/agents-cli.js +362 -0
- package/dist/apps-cli.d.ts +2 -0
- package/dist/apps-cli.js +173 -0
- package/dist/builds/index.d.ts +10 -0
- package/dist/builds/index.js +11 -0
- package/dist/cli-words.js +1 -0
- package/dist/cli.js +88 -6
- package/dist/client.d.ts +19 -0
- package/dist/client.js +20 -0
- package/dist/cloudflare/errors.d.ts +23 -0
- package/dist/cloudflare/errors.js +16 -0
- package/dist/cloudflare/index.d.ts +82 -9
- package/dist/cloudflare/index.js +162 -38
- package/dist/cloudflare/interpreter.js +14 -5
- package/dist/cloudflare/mime.d.ts +1 -0
- package/dist/cloudflare/mime.js +66 -0
- package/dist/cloudflare/streams.d.ts +8 -0
- package/dist/cloudflare/streams.js +30 -0
- package/dist/cloudflare/types.d.ts +338 -0
- package/dist/cloudflare/types.js +80 -0
- package/dist/cloudflare/worker.d.ts +297 -10
- package/dist/cloudflare/worker.js +203 -17
- package/dist/containers/index.d.ts +10 -0
- package/dist/containers/index.js +11 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.js +1 -0
- package/dist/product-names.js +3 -0
- package/dist/products/agents.d.ts +272 -0
- package/dist/products/agents.js +251 -0
- package/dist/products/containers.d.ts +71 -0
- package/dist/products/containers.js +6 -0
- package/dist/products/index.d.ts +6 -0
- package/dist/products/index.js +7 -0
- package/dist/sandbox.d.ts +4 -0
- package/dist/transport.d.ts +2 -2
- package/dist/transport.js +1 -1
- package/dist/tunnel.js +1 -1
- package/dist/types.d.ts +11 -0
- package/package.json +16 -1
|
@@ -0,0 +1,251 @@
|
|
|
1
|
+
/** Agents: a coding or support agent's harness (Claude Code, Codex, Gemini
|
|
2
|
+
* CLI, or your own code on an agents SDK) in a sandbox of its own per
|
|
3
|
+
* session, on your own model key. Your app drives its sessions through this
|
|
4
|
+
* API and webhooks. In a private beta: outside it every call is refused with
|
|
5
|
+
* `product_in_beta`.
|
|
6
|
+
*
|
|
7
|
+
* const agent = await runtime.agents.create({
|
|
8
|
+
* name: "support",
|
|
9
|
+
* definition: {
|
|
10
|
+
* ...runtime.agents.templates["claude-code"].definition,
|
|
11
|
+
* ...runtime.agents.uses.support.definition,
|
|
12
|
+
* instructions: "Answer questions about our product. Be brief.",
|
|
13
|
+
* },
|
|
14
|
+
* });
|
|
15
|
+
* const session = await runtime.agents.start("support", { input: "Hi!", key: "customer:42" });
|
|
16
|
+
* for await (const event of session.events()) if (event.kind === "reply") console.log(event.body.text);
|
|
17
|
+
*
|
|
18
|
+
* A session's sandbox is billed while it runs, at $0.03 per active vCPU-hour
|
|
19
|
+
* and $0.01 per GiB-hour of memory; a waiting session's sandbox is paused.
|
|
20
|
+
* No session fee, no seats. */
|
|
21
|
+
import { Page } from "../page.js";
|
|
22
|
+
const START = 'npx -y @anthropic-ai/claude-code --dangerously-skip-permissions --mcp-config ~/.runtime-agent/mcp.json -p "$(cat ~/.runtime-agent/start.md)"';
|
|
23
|
+
const CODEX = 'npx -y @openai/codex exec --dangerously-bypass-approvals-and-sandbox "$(cat ~/.runtime-agent/start.md)"';
|
|
24
|
+
const GEMINI = 'npx -y @google/gemini-cli --yolo -p "$(cat ~/.runtime-agent/start.md)"';
|
|
25
|
+
/** The five harnesses (agents-contract.md); tests/agents.test.ts holds them
|
|
26
|
+
* to packages/cloud-guide/agent-templates.json. */
|
|
27
|
+
export const AGENT_TEMPLATES = {
|
|
28
|
+
"claude-code": {
|
|
29
|
+
key: "claude-code",
|
|
30
|
+
title: "Claude Code",
|
|
31
|
+
command: START,
|
|
32
|
+
apiKeySecret: "ANTHROPIC_API_KEY",
|
|
33
|
+
apiKeyHost: "api.anthropic.com",
|
|
34
|
+
subscription: "token: run `claude setup-token` on your own computer (Pro/Max), then `runtime secrets set CLAUDE_CODE_OAUTH_TOKEN` scoped to api.anthropic.com",
|
|
35
|
+
definition: { command: START, secrets: ["ANTHROPIC_API_KEY"] },
|
|
36
|
+
},
|
|
37
|
+
codex: {
|
|
38
|
+
key: "codex",
|
|
39
|
+
title: "Codex CLI",
|
|
40
|
+
command: CODEX,
|
|
41
|
+
apiKeySecret: "OPENAI_API_KEY",
|
|
42
|
+
apiKeyHost: "api.openai.com",
|
|
43
|
+
subscription: "login once in the sandbox's terminal: `npx -y @openai/codex login --device-auth`, kept in the snapshot or a volume at `~/.codex`",
|
|
44
|
+
definition: { command: CODEX, secrets: ["OPENAI_API_KEY"] },
|
|
45
|
+
},
|
|
46
|
+
"gemini-cli": {
|
|
47
|
+
key: "gemini-cli",
|
|
48
|
+
title: "Gemini CLI",
|
|
49
|
+
command: GEMINI,
|
|
50
|
+
apiKeySecret: "GEMINI_API_KEY",
|
|
51
|
+
apiKeyHost: "generativelanguage.googleapis.com",
|
|
52
|
+
subscription: "login once in the sandbox's terminal (Sign in with Google), kept at `~/.gemini`",
|
|
53
|
+
definition: { command: GEMINI, secrets: ["GEMINI_API_KEY"] },
|
|
54
|
+
},
|
|
55
|
+
"claude-agent-sdk": {
|
|
56
|
+
key: "claude-agent-sdk",
|
|
57
|
+
title: "Claude Agent SDK",
|
|
58
|
+
command: "python3 ~/agent.py",
|
|
59
|
+
apiKeySecret: "ANTHROPIC_API_KEY",
|
|
60
|
+
apiKeyHost: "api.anthropic.com",
|
|
61
|
+
subscription: null,
|
|
62
|
+
definition: { command: "python3 ~/agent.py", secrets: ["ANTHROPIC_API_KEY"] },
|
|
63
|
+
},
|
|
64
|
+
"openai-agents-sdk": {
|
|
65
|
+
key: "openai-agents-sdk",
|
|
66
|
+
title: "OpenAI Agents SDK",
|
|
67
|
+
command: "python3 ~/agent.py",
|
|
68
|
+
apiKeySecret: "OPENAI_API_KEY",
|
|
69
|
+
apiKeyHost: "api.openai.com",
|
|
70
|
+
subscription: null,
|
|
71
|
+
definition: { command: "python3 ~/agent.py", secrets: ["OPENAI_API_KEY"] },
|
|
72
|
+
},
|
|
73
|
+
};
|
|
74
|
+
export const AGENT_USES = {
|
|
75
|
+
support: {
|
|
76
|
+
key: "support",
|
|
77
|
+
title: "Your customers",
|
|
78
|
+
sessionKey: "customer:<id>",
|
|
79
|
+
triggers: ["api", "webhook"],
|
|
80
|
+
definition: {
|
|
81
|
+
template: "support",
|
|
82
|
+
vcpu: 1,
|
|
83
|
+
memoryMiB: 1024,
|
|
84
|
+
idlePauseSeconds: 10,
|
|
85
|
+
maxConcurrent: 1000,
|
|
86
|
+
},
|
|
87
|
+
},
|
|
88
|
+
team: {
|
|
89
|
+
key: "team",
|
|
90
|
+
title: "Your team",
|
|
91
|
+
sessionKey: null,
|
|
92
|
+
triggers: ["slack", "github"],
|
|
93
|
+
definition: { template: "team", vcpu: 4, memoryMiB: 8192 },
|
|
94
|
+
},
|
|
95
|
+
};
|
|
96
|
+
const enc = encodeURIComponent;
|
|
97
|
+
const ENDED = ["done", "failed", "stopped"];
|
|
98
|
+
export function agents(t) {
|
|
99
|
+
const getSession = (id, options) => t.json({ method: "GET", path: `/v1/agents/sessions/${enc(id)}`, ...options });
|
|
100
|
+
async function* events(id, options = {}) {
|
|
101
|
+
let after = options.after ?? 0;
|
|
102
|
+
for (;;) {
|
|
103
|
+
options.signal?.throwIfAborted();
|
|
104
|
+
const read = await t.json({
|
|
105
|
+
method: "GET",
|
|
106
|
+
path: `/v1/agents/sessions/${enc(id)}/events`,
|
|
107
|
+
query: { after, wait: 30 },
|
|
108
|
+
...(options.signal ? { signal: options.signal } : {}),
|
|
109
|
+
timeoutMs: 0,
|
|
110
|
+
});
|
|
111
|
+
for (const event of read.data) {
|
|
112
|
+
after = event.seq;
|
|
113
|
+
yield event;
|
|
114
|
+
}
|
|
115
|
+
if (read.ended)
|
|
116
|
+
return;
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
const handle = (session, joined = false, seq = session.lastSeq) => ({
|
|
120
|
+
id: session.id,
|
|
121
|
+
session,
|
|
122
|
+
joined,
|
|
123
|
+
seq,
|
|
124
|
+
send: (text, options) => t.json({
|
|
125
|
+
method: "POST",
|
|
126
|
+
path: `/v1/agents/sessions/${enc(session.id)}/messages`,
|
|
127
|
+
body: { text },
|
|
128
|
+
...options,
|
|
129
|
+
}),
|
|
130
|
+
events: (options) => events(session.id, options),
|
|
131
|
+
stop: (options) => t.json({
|
|
132
|
+
method: "POST",
|
|
133
|
+
path: `/v1/agents/sessions/${enc(session.id)}/stop`,
|
|
134
|
+
body: {},
|
|
135
|
+
...options,
|
|
136
|
+
}),
|
|
137
|
+
async wait(options = {}) {
|
|
138
|
+
const now = await getSession(session.id, options);
|
|
139
|
+
if (ENDED.includes(now.state))
|
|
140
|
+
return now;
|
|
141
|
+
for await (const _ of events(session.id, { after: now.lastSeq, ...options }))
|
|
142
|
+
;
|
|
143
|
+
return getSession(session.id, options);
|
|
144
|
+
},
|
|
145
|
+
get: (options) => getSession(session.id, options),
|
|
146
|
+
});
|
|
147
|
+
const list = async (query = {}, options) => {
|
|
148
|
+
const page = await t.json({
|
|
149
|
+
method: "GET",
|
|
150
|
+
path: "/v1/agents",
|
|
151
|
+
query,
|
|
152
|
+
...options,
|
|
153
|
+
});
|
|
154
|
+
return new Page(page.data, page.nextCursor, (cursor) => list({ ...query, cursor }, options));
|
|
155
|
+
};
|
|
156
|
+
const listSessions = async (query = {}, options) => {
|
|
157
|
+
const page = await t.json({
|
|
158
|
+
method: "GET",
|
|
159
|
+
path: "/v1/agents/sessions",
|
|
160
|
+
query,
|
|
161
|
+
...options,
|
|
162
|
+
});
|
|
163
|
+
return new Page(page.data, page.nextCursor, (cursor) => listSessions({ ...query, cursor }, options));
|
|
164
|
+
};
|
|
165
|
+
return {
|
|
166
|
+
/** An agent: a name and a definition its sessions start from. */
|
|
167
|
+
create: (input, options) => t.json({ method: "POST", path: "/v1/agents", body: input, ...options }),
|
|
168
|
+
/** By its id or its name. */
|
|
169
|
+
get: (agent, options) => t.json({ method: "GET", path: `/v1/agents/${enc(agent)}`, ...options }),
|
|
170
|
+
/** Your agents, oldest first. Await for a page, or `for await` for all. */
|
|
171
|
+
list,
|
|
172
|
+
/** A new version of the definition, whole; sessions already started keep theirs. */
|
|
173
|
+
update: (agent, definition, options) => t.json({
|
|
174
|
+
method: "PATCH",
|
|
175
|
+
path: `/v1/agents/${enc(agent)}`,
|
|
176
|
+
body: { definition },
|
|
177
|
+
...options,
|
|
178
|
+
}),
|
|
179
|
+
/** Its triggers go and its open sessions stop. */
|
|
180
|
+
delete: async (agent, options) => {
|
|
181
|
+
await t.json({ method: "DELETE", path: `/v1/agents/${enc(agent)}`, ...options });
|
|
182
|
+
},
|
|
183
|
+
/** A session with its first words, or the open one with the same key joined. */
|
|
184
|
+
async start(agent, input, options) {
|
|
185
|
+
const out = await t.json({
|
|
186
|
+
method: "POST",
|
|
187
|
+
path: `/v1/agents/${enc(agent)}/sessions`,
|
|
188
|
+
body: input,
|
|
189
|
+
...options,
|
|
190
|
+
});
|
|
191
|
+
return handle(out.session, out.joined, out.seq);
|
|
192
|
+
},
|
|
193
|
+
/** A session you already have, by its id. */
|
|
194
|
+
async session(id, options) {
|
|
195
|
+
return handle(await getSession(id, options));
|
|
196
|
+
},
|
|
197
|
+
sessions: {
|
|
198
|
+
get: getSession,
|
|
199
|
+
/** Newest first; of one agent, or in some states. */
|
|
200
|
+
list: listSessions,
|
|
201
|
+
/** An ended session and its log go. Its history is storage like any
|
|
202
|
+
* other, kept until you delete it; an open session is refused
|
|
203
|
+
* (`session_open`): stop it first. */
|
|
204
|
+
delete: async (id, options) => {
|
|
205
|
+
await t.json({
|
|
206
|
+
method: "DELETE",
|
|
207
|
+
path: `/v1/agents/sessions/${enc(id)}`,
|
|
208
|
+
...options,
|
|
209
|
+
});
|
|
210
|
+
},
|
|
211
|
+
},
|
|
212
|
+
triggers: {
|
|
213
|
+
create: (agent, input, options) => t.json({
|
|
214
|
+
method: "POST",
|
|
215
|
+
path: `/v1/agents/${enc(agent)}/triggers`,
|
|
216
|
+
body: input,
|
|
217
|
+
...options,
|
|
218
|
+
}),
|
|
219
|
+
list: async (agent, options) => (await t.json({
|
|
220
|
+
method: "GET",
|
|
221
|
+
path: `/v1/agents/${enc(agent)}/triggers`,
|
|
222
|
+
...options,
|
|
223
|
+
})).data,
|
|
224
|
+
/** Its events are refused, saying `why`; nothing else is held. */
|
|
225
|
+
pause: (id, why, options) => t.json({
|
|
226
|
+
method: "POST",
|
|
227
|
+
path: `/v1/agents/triggers/${enc(id)}/pause`,
|
|
228
|
+
body: { why },
|
|
229
|
+
...options,
|
|
230
|
+
}),
|
|
231
|
+
resume: (id, options) => t.json({
|
|
232
|
+
method: "POST",
|
|
233
|
+
path: `/v1/agents/triggers/${enc(id)}/resume`,
|
|
234
|
+
body: {},
|
|
235
|
+
...options,
|
|
236
|
+
}),
|
|
237
|
+
delete: async (id, options) => {
|
|
238
|
+
await t.json({
|
|
239
|
+
method: "DELETE",
|
|
240
|
+
path: `/v1/agents/triggers/${enc(id)}`,
|
|
241
|
+
...options,
|
|
242
|
+
});
|
|
243
|
+
},
|
|
244
|
+
},
|
|
245
|
+
/** The harnesses, as data: claude-code, codex, gemini-cli,
|
|
246
|
+
* claude-agent-sdk, openai-agents-sdk. */
|
|
247
|
+
templates: AGENT_TEMPLATES,
|
|
248
|
+
/** The uses, as data: support (your customers) and team (your team). */
|
|
249
|
+
uses: AGENT_USES,
|
|
250
|
+
};
|
|
251
|
+
}
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
/** Containers: one OCI image's process on its own microVM, billed at the
|
|
2
|
+
* sandbox rates (packages/cloud/src/api/products/containers.ts), at
|
|
3
|
+
* /v1/containers. In a private beta: an account outside it is refused with
|
|
4
|
+
* product_in_beta (403), and retrying does not change it. */
|
|
5
|
+
import type { Transport } from "../transport.js";
|
|
6
|
+
import { type ResourceRecord } from "./resources.js";
|
|
7
|
+
export type ContainerState = "waiting" | "running" | "sleeping" | "stopped" | "failed" | "deleting" | "deleted";
|
|
8
|
+
export type Container = ResourceRecord & {
|
|
9
|
+
name: string | null;
|
|
10
|
+
labels: Record<string, string>;
|
|
11
|
+
state: ContainerState;
|
|
12
|
+
createdAt: number;
|
|
13
|
+
updatedAt: number;
|
|
14
|
+
deletedAt: number | null;
|
|
15
|
+
/** The image it runs, pinned to its digest (name@sha256:...). */
|
|
16
|
+
image: string;
|
|
17
|
+
entrypoint: string[];
|
|
18
|
+
command: string[];
|
|
19
|
+
workingDir: string;
|
|
20
|
+
user: string;
|
|
21
|
+
/** The TCP port it serves on, or null when it serves none. */
|
|
22
|
+
port: number | null;
|
|
23
|
+
/** The image's exposed ports, as N/tcp or N/udp. */
|
|
24
|
+
exposedPorts: string[];
|
|
25
|
+
onExit: "restart" | "stop";
|
|
26
|
+
sleep: boolean;
|
|
27
|
+
vcpu: number;
|
|
28
|
+
memoryMiB: number;
|
|
29
|
+
/** The environment's names. Values are never answered: they may be secrets. */
|
|
30
|
+
envNames: string[];
|
|
31
|
+
};
|
|
32
|
+
export type CreateContainer = {
|
|
33
|
+
/** An OCI image reference; the answer pins its digest. */
|
|
34
|
+
image: string;
|
|
35
|
+
/** 1 to 16. */
|
|
36
|
+
vcpu: number;
|
|
37
|
+
/** 128 to 65536 MiB. */
|
|
38
|
+
memoryMiB: number;
|
|
39
|
+
name?: string;
|
|
40
|
+
labels?: Record<string, string>;
|
|
41
|
+
/** Replaces the image's Entrypoint and drops its Cmd. */
|
|
42
|
+
entrypoint?: string[];
|
|
43
|
+
/** Replaces the image's Cmd; keeps the effective entrypoint. */
|
|
44
|
+
command?: string[];
|
|
45
|
+
/** Set over the image's own environment. */
|
|
46
|
+
env?: Record<string, string>;
|
|
47
|
+
/** An absolute path; the image's, else /. */
|
|
48
|
+
workingDir?: string;
|
|
49
|
+
/** The image's, else root. */
|
|
50
|
+
user?: string;
|
|
51
|
+
/** 1 to 65535. Required when the image exposes several TCP ports. */
|
|
52
|
+
port?: number;
|
|
53
|
+
/** Default: restart when it serves a port, otherwise stop. */
|
|
54
|
+
onExit?: "restart" | "stop";
|
|
55
|
+
/** Sleep when idle; false by default. */
|
|
56
|
+
sleep?: boolean;
|
|
57
|
+
};
|
|
58
|
+
/** Only the name and labels change; a null name clears it. */
|
|
59
|
+
export type UpdateContainer = {
|
|
60
|
+
name?: string | null;
|
|
61
|
+
labels?: Record<string, string>;
|
|
62
|
+
};
|
|
63
|
+
export declare function containers(t: Transport): {
|
|
64
|
+
base: string;
|
|
65
|
+
create: (input: CreateContainer, options?: import("../transport.js").RequestOptions) => Promise<Container>;
|
|
66
|
+
get: (id: string, options?: import("./resources.js").ResourceGetOptions<"stopped" | "running" | "deleted" | "failed" | "deleting" | "waiting" | "sleeping">) => Promise<Container>;
|
|
67
|
+
list: (query?: import("./resources.js").ResourceListQuery<"stopped" | "running" | "deleted" | "failed" | "deleting" | "waiting" | "sleeping">, options?: import("../transport.js").RequestOptions) => Promise<import("../page.js").Page<Container>>;
|
|
68
|
+
update: (id: string, input: UpdateContainer, options?: import("../transport.js").RequestOptions) => Promise<Container>;
|
|
69
|
+
wait: (id: string, target: "stopped" | "running" | "deleted" | "failed" | "deleting" | "waiting" | "sleeping", options?: import("./resources.js").ResourceWaitOptions) => Promise<Container>;
|
|
70
|
+
delete: (id: string, options?: import("./resources.js").ResourceDeleteOptions) => Promise<Container>;
|
|
71
|
+
};
|
package/dist/products/index.d.ts
CHANGED
|
@@ -21,6 +21,9 @@ import { sandboxTailscale } from "./tailscale.js";
|
|
|
21
21
|
import { secrets } from "./secrets.js";
|
|
22
22
|
import { mcp, sandboxMcp } from "./mcp.js";
|
|
23
23
|
import { events, otel, sandboxMetrics, webhooks } from "./observability.js";
|
|
24
|
+
import { agents } from "./agents.js";
|
|
25
|
+
import { builds } from "./builds.js";
|
|
26
|
+
import { containers } from "./containers.js";
|
|
24
27
|
export declare const clientExtensions: {
|
|
25
28
|
images: typeof images;
|
|
26
29
|
volumes: typeof volumes;
|
|
@@ -41,6 +44,9 @@ export declare const clientExtensions: {
|
|
|
41
44
|
ports: typeof ports;
|
|
42
45
|
ips: typeof ips;
|
|
43
46
|
networks: typeof networks;
|
|
47
|
+
agents: typeof agents;
|
|
48
|
+
builds: typeof builds;
|
|
49
|
+
containers: typeof containers;
|
|
44
50
|
};
|
|
45
51
|
export declare const sandboxExtensions: {
|
|
46
52
|
interpreter: typeof sandboxInterpreter;
|
package/dist/products/index.js
CHANGED
|
@@ -19,6 +19,9 @@ import { sandboxTailscale } from "./tailscale.js";
|
|
|
19
19
|
import { secrets } from "./secrets.js";
|
|
20
20
|
import { mcp, sandboxMcp } from "./mcp.js";
|
|
21
21
|
import { events, otel, sandboxMetrics, webhooks } from "./observability.js";
|
|
22
|
+
import { agents } from "./agents.js";
|
|
23
|
+
import { builds } from "./builds.js";
|
|
24
|
+
import { containers } from "./containers.js";
|
|
22
25
|
/* HOW A LANE ADDS A PRODUCT TO THE SDK
|
|
23
26
|
*
|
|
24
27
|
* 1. Write src/products/<name>.ts exporting a factory:
|
|
@@ -54,6 +57,10 @@ export const clientExtensions = {
|
|
|
54
57
|
ports,
|
|
55
58
|
ips,
|
|
56
59
|
networks,
|
|
60
|
+
agents,
|
|
61
|
+
// Builds (beta): the API answers product_in_beta outside its list.
|
|
62
|
+
builds,
|
|
63
|
+
containers,
|
|
57
64
|
};
|
|
58
65
|
export const sandboxExtensions = {
|
|
59
66
|
interpreter: sandboxInterpreter,
|
package/dist/sandbox.d.ts
CHANGED
|
@@ -95,12 +95,15 @@ export declare class Sandbox extends Machine<SandboxInfo, SandboxSettings, Delet
|
|
|
95
95
|
* each its own sandbox, answered once they run. A running sandbox is paused
|
|
96
96
|
* for the moment its snapshot takes, then woken. One without `count`; an
|
|
97
97
|
* array with it. `funding` is what the copies run on, as for a create;
|
|
98
|
+
* omitted, they keep this sandbox's. `secrets` names the egress secrets the
|
|
99
|
+
* copies may use, and may only narrow this sandbox's list: [] is none;
|
|
98
100
|
* omitted, they keep this sandbox's. */
|
|
99
101
|
fork(options?: {
|
|
100
102
|
name?: string;
|
|
101
103
|
labels?: Record<string, string>;
|
|
102
104
|
keepSnapshot?: boolean;
|
|
103
105
|
funding?: "trial" | "paid";
|
|
106
|
+
secrets?: string[];
|
|
104
107
|
} & RequestOptions): Promise<Sandbox>;
|
|
105
108
|
fork(options: {
|
|
106
109
|
count: number;
|
|
@@ -108,6 +111,7 @@ export declare class Sandbox extends Machine<SandboxInfo, SandboxSettings, Delet
|
|
|
108
111
|
labels?: Record<string, string>;
|
|
109
112
|
keepSnapshot?: boolean;
|
|
110
113
|
funding?: "trial" | "paid";
|
|
114
|
+
secrets?: string[];
|
|
111
115
|
} & RequestOptions): Promise<Sandbox[]>;
|
|
112
116
|
}
|
|
113
117
|
/** A sandbox session, as the API answers it. `token` is set only in the
|
package/dist/transport.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { RuntimeError } from "./errors.js";
|
|
2
|
-
export declare const VERSION = "0.
|
|
2
|
+
export declare const VERSION = "0.21.0";
|
|
3
3
|
export declare const DEFAULT_BASE_URL = "https://api.withruntime.com";
|
|
4
4
|
/** Runtime's API as code inside a Runtime sandbox reaches it: the sandbox's
|
|
5
5
|
* own host sends each request on to DEFAULT_BASE_URL over HTTPS. The API runs
|
|
@@ -38,7 +38,7 @@ export type Query = Record<string, string | number | boolean | readonly string[]
|
|
|
38
38
|
export type Call = RequestOptions & {
|
|
39
39
|
/** Internal protocol hook: successful headers arrived, before reading the body. */
|
|
40
40
|
onResponse?: (response: Response) => void;
|
|
41
|
-
method: "GET" | "POST" | "PUT" | "DELETE";
|
|
41
|
+
method: "GET" | "POST" | "PUT" | "PATCH" | "DELETE";
|
|
42
42
|
path: string;
|
|
43
43
|
query?: Query;
|
|
44
44
|
body?: unknown;
|
package/dist/transport.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { ConnectionError, DELIBERATE, errorFor, NOTHING_RAN, RuntimeError, WAITS_FOR_ROOM, } from "./errors.js";
|
|
2
2
|
import { describeRoute, envFetch, openWebSocket } from "./proxy.js";
|
|
3
3
|
import { warningText } from "./product-renames.js";
|
|
4
|
-
export const VERSION = "0.
|
|
4
|
+
export const VERSION = "0.21.0";
|
|
5
5
|
export const DEFAULT_BASE_URL = "https://api.withruntime.com";
|
|
6
6
|
/** Runtime's API as code inside a Runtime sandbox reaches it: the sandbox's
|
|
7
7
|
* own host sends each request on to DEFAULT_BASE_URL over HTTPS. The API runs
|
package/dist/tunnel.js
CHANGED
|
@@ -235,7 +235,7 @@ export class Tunnel {
|
|
|
235
235
|
message: "The sandbox has no OpenSSH server (sshd).",
|
|
236
236
|
code: "sshd_missing",
|
|
237
237
|
status: 0,
|
|
238
|
-
hint: "Install it once: sudo apt-get install -y openssh-server",
|
|
238
|
+
hint: "Install it once: sudo apt-get update && sudo apt-get install -y openssh-server",
|
|
239
239
|
})
|
|
240
240
|
: new RuntimeError({
|
|
241
241
|
message: `The sandbox refused the connection (${error.message}).`,
|
package/dist/types.d.ts
CHANGED
|
@@ -62,6 +62,12 @@ export type SandboxInfo = {
|
|
|
62
62
|
/** The names of its own environment variables (`env`), on a create, an
|
|
63
63
|
* update and a read of one sandbox. Values are never shown. */
|
|
64
64
|
envNames?: string[];
|
|
65
|
+
/** The egress secrets this sandbox may use, by name: only those of your
|
|
66
|
+
* egress secrets that would otherwise reach it. Null is every secret that
|
|
67
|
+
* reaches it. Fixed for the sandbox's life; a fork or a copy of a snapshot
|
|
68
|
+
* may only narrow its source's list. On a create, an update, a fork and a
|
|
69
|
+
* read of one sandbox; absent from list pages and older servers. */
|
|
70
|
+
secrets?: string[] | null;
|
|
65
71
|
/** On an update with labels by a key that may read secrets, when one of
|
|
66
72
|
* the account's egress secrets is scoped: true once every server running its sandboxes holds the change,
|
|
67
73
|
* so the next request uses the new scope; false while one has not
|
|
@@ -102,6 +108,11 @@ export type CreateSandbox = {
|
|
|
102
108
|
* `env`. At most 32 variables and 32 KiB. Values are never shown again;
|
|
103
109
|
* answers list only `envNames`. Copies made by fork() keep them. */
|
|
104
110
|
env?: Record<string, string>;
|
|
111
|
+
/** The egress secrets this sandbox may use, by name: only those of your
|
|
112
|
+
* egress secrets that would otherwise reach it. [] is none; leave it out
|
|
113
|
+
* for every secret that reaches it. Fixed for the sandbox's life; a fork or
|
|
114
|
+
* a copy of a snapshot may only narrow its source's list. At most 64. */
|
|
115
|
+
secrets?: string[];
|
|
105
116
|
/** Omit to use the free usage while it lasts, then prepaid credit. */
|
|
106
117
|
funding?: "trial" | "paid";
|
|
107
118
|
region?: string;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "withruntime",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.21.0",
|
|
4
4
|
"license": "Apache-2.0",
|
|
5
5
|
"mcpName": "com.withruntime/runtime",
|
|
6
6
|
"type": "module",
|
|
@@ -55,6 +55,21 @@
|
|
|
55
55
|
"import": "./dist/networks/index.js",
|
|
56
56
|
"default": "./dist/networks/index.js"
|
|
57
57
|
},
|
|
58
|
+
"./agents": {
|
|
59
|
+
"types": "./dist/agents/index.d.ts",
|
|
60
|
+
"import": "./dist/agents/index.js",
|
|
61
|
+
"default": "./dist/agents/index.js"
|
|
62
|
+
},
|
|
63
|
+
"./containers": {
|
|
64
|
+
"types": "./dist/containers/index.d.ts",
|
|
65
|
+
"import": "./dist/containers/index.js",
|
|
66
|
+
"default": "./dist/containers/index.js"
|
|
67
|
+
},
|
|
68
|
+
"./builds": {
|
|
69
|
+
"types": "./dist/builds/index.d.ts",
|
|
70
|
+
"import": "./dist/builds/index.js",
|
|
71
|
+
"default": "./dist/builds/index.js"
|
|
72
|
+
},
|
|
58
73
|
"./e2b": {
|
|
59
74
|
"types": "./dist/e2b/index.d.ts",
|
|
60
75
|
"import": "./dist/e2b/index.js",
|