@sandboxrouter/sdk 0.2.0 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +229 -50
- package/dist/bench.js +4 -4
- package/dist/catalog.d.ts +159 -0
- package/dist/catalog.js +450 -15
- package/dist/check.d.ts +28 -0
- package/dist/check.js +185 -0
- package/dist/cli.js +171 -12
- package/dist/computers.d.ts +55 -13
- package/dist/computers.js +132 -6
- package/dist/conformance.d.ts +46 -0
- package/dist/conformance.js +65 -0
- package/dist/cost.d.ts +67 -0
- package/dist/cost.js +153 -0
- package/dist/gc.d.ts +29 -0
- package/dist/gc.js +54 -0
- package/dist/index.d.ts +28 -2
- package/dist/index.js +28 -2
- package/dist/leaderboard.d.ts +6 -0
- package/dist/leaderboard.js +5 -4
- package/dist/ledger.d.ts +38 -0
- package/dist/ledger.js +89 -0
- package/dist/providers/agent37.d.ts +40 -0
- package/dist/providers/agent37.js +224 -0
- package/dist/providers/agentcore.d.ts +71 -0
- package/dist/providers/agentcore.js +446 -0
- package/dist/providers/alibaba.d.ts +18 -0
- package/dist/providers/alibaba.js +106 -0
- package/dist/providers/azure.d.ts +43 -0
- package/dist/providers/azure.js +330 -0
- package/dist/providers/beam.d.ts +11 -0
- package/dist/providers/beam.js +179 -0
- package/dist/providers/blaxel.d.ts +3 -1
- package/dist/providers/blaxel.js +32 -22
- package/dist/providers/boat.js +8 -3
- package/dist/providers/cloudflare.js +8 -3
- package/dist/providers/codesandbox.d.ts +59 -0
- package/dist/providers/codesandbox.js +287 -0
- package/dist/providers/daytona.d.ts +25 -4
- package/dist/providers/daytona.js +449 -28
- package/dist/providers/dedalus.d.ts +12 -0
- package/dist/providers/dedalus.js +244 -0
- package/dist/providers/deno.d.ts +50 -0
- package/dist/providers/deno.js +170 -0
- package/dist/providers/docker.js +11 -5
- package/dist/providers/e2b.d.ts +70 -3
- package/dist/providers/e2b.js +376 -8
- package/dist/providers/exedev.js +17 -5
- package/dist/providers/freestyle.d.ts +49 -0
- package/dist/providers/freestyle.js +261 -0
- package/dist/providers/hopx.js +27 -18
- package/dist/providers/instabox.d.ts +76 -0
- package/dist/providers/instabox.js +360 -0
- package/dist/providers/koyeb.d.ts +71 -0
- package/dist/providers/koyeb.js +379 -0
- package/dist/providers/lambda.d.ts +51 -0
- package/dist/providers/lambda.js +467 -0
- package/dist/providers/langsmith.d.ts +16 -0
- package/dist/providers/langsmith.js +149 -0
- package/dist/providers/limrun.d.ts +77 -0
- package/dist/providers/limrun.js +626 -0
- package/dist/providers/maritime.d.ts +5 -1
- package/dist/providers/maritime.js +39 -8
- package/dist/providers/mobilerun.d.ts +44 -0
- package/dist/providers/mobilerun.js +417 -0
- package/dist/providers/modal.js +12 -4
- package/dist/providers/morph.js +12 -4
- package/dist/providers/northflank.js +11 -13
- package/dist/providers/novita.d.ts +12 -0
- package/dist/providers/novita.js +81 -0
- package/dist/providers/openscale.d.ts +17 -0
- package/dist/providers/openscale.js +87 -0
- package/dist/providers/orgo.d.ts +45 -0
- package/dist/providers/orgo.js +414 -0
- package/dist/providers/sail.d.ts +32 -0
- package/dist/providers/sail.js +372 -0
- package/dist/providers/superserve.d.ts +25 -0
- package/dist/providers/superserve.js +337 -0
- package/dist/providers/tensorlake.js +17 -14
- package/dist/providers/upstash.d.ts +30 -0
- package/dist/providers/upstash.js +258 -0
- package/dist/providers/vercel.js +14 -3
- package/dist/providers/workspaces.d.ts +60 -0
- package/dist/providers/workspaces.js +662 -0
- package/dist/router.d.ts +41 -5
- package/dist/router.js +179 -23
- package/dist/server.d.ts +1 -1
- package/dist/server.js +22 -3
- package/dist/types.d.ts +13 -5
- package/dist/util.d.ts +28 -1
- package/dist/util.js +56 -7
- package/package.json +81 -5
package/dist/catalog.js
CHANGED
|
@@ -1,3 +1,30 @@
|
|
|
1
|
+
import { KOYEB_INSTANCES, koyebInstance } from "./providers/koyeb.js";
|
|
2
|
+
import { AGENT37_SHAPES, agent37Shape } from "./providers/agent37.js";
|
|
3
|
+
import { INSTABOX_SIZES, instaboxSize } from "./providers/instabox.js";
|
|
4
|
+
import { FREESTYLE_SIZES, freestyleSize } from "./providers/freestyle.js";
|
|
5
|
+
import { langsmithSize } from "./providers/langsmith.js";
|
|
6
|
+
/** Short label for a gated provider's sign-up status, or null when anyone can sign up. */
|
|
7
|
+
export function accessLabel(id) {
|
|
8
|
+
const a = CATALOG.find((c) => c.id === id)?.access;
|
|
9
|
+
return a ? (a.status === "waitlist" ? "sign-up waitlisted" : "not taking new accounts") : null;
|
|
10
|
+
}
|
|
11
|
+
/** Short label for the plan a provider needs before you can use it: "none", "$20/mo (credited)", "$5/mo". */
|
|
12
|
+
export function planLabel(id) {
|
|
13
|
+
const p = CATALOG.find((c) => c.id === id)?.plan;
|
|
14
|
+
if (!p)
|
|
15
|
+
return "none";
|
|
16
|
+
return `${p.unclear ? "maybe " : ""}$${p.usdMonth}/mo${p.credited ? " (credited)" : ""}`;
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* The order tables list providers in (README, CLI, website): providers anyone can sign up for that can
|
|
20
|
+
* take this size, cheapest first, ties alphabetical; then waitlisted or closed sign-ups; then providers
|
|
21
|
+
* that can't take the size; then Docker. The router uses the same price order, but only among providers
|
|
22
|
+
* you have keys for, so a gated provider only gets work if you already have an account there.
|
|
23
|
+
*/
|
|
24
|
+
export function listingOrder(spec = { vcpu: DEFAULT_VCPU, memoryGb: DEFAULT_MEMORY_GB }) {
|
|
25
|
+
const rank = (c) => (c.local ? 3 : unfit(c.id, spec) ? 2 : c.access ? 1 : 0);
|
|
26
|
+
return [...CATALOG].sort((a, b) => rank(a) - rank(b) || hourlyCost(a.id, spec) - hourlyCost(b.id, spec) || a.id.localeCompare(b.id));
|
|
27
|
+
}
|
|
1
28
|
/**
|
|
2
29
|
* Every provider is treated the same: the router orders candidates by list price for the requested
|
|
3
30
|
* size (or by your measured cold starts), ties broken alphabetically. Nobody gets a better slot.
|
|
@@ -26,9 +53,9 @@ const ENTRIES = [
|
|
|
26
53
|
pricing: {
|
|
27
54
|
vcpuHour: 0.0055,
|
|
28
55
|
gbHour: 0.00275,
|
|
29
|
-
note: "per second, disk included",
|
|
56
|
+
note: "per second, no minimum runtime; running disk included; Starter $20/mo incl. $20 usage; paused disk $0.08/GB-month (default idle action deletes sandbox)",
|
|
30
57
|
source: "https://maritime.sh/pricing",
|
|
31
|
-
checked: "2026-11-
|
|
58
|
+
checked: "2026-11-05",
|
|
32
59
|
},
|
|
33
60
|
capabilities: ["pause", "custom-image"],
|
|
34
61
|
limits: { maxVcpu: 16, maxMemoryGb: 64 },
|
|
@@ -41,12 +68,14 @@ const ENTRIES = [
|
|
|
41
68
|
pricing: {
|
|
42
69
|
vcpuHour: 0.0504,
|
|
43
70
|
gbHour: 0.0162,
|
|
44
|
-
note: "per second;
|
|
71
|
+
note: "per second; free Hobby tier ($100 one-time credit, 1-hour sessions, 20 at once); Pro $150/mo for longer sessions",
|
|
45
72
|
source: "https://e2b.dev/pricing",
|
|
46
73
|
checked: "2026-11-04",
|
|
47
74
|
},
|
|
48
75
|
capabilities: ["pause", "custom-image"],
|
|
49
76
|
limits: { maxVcpu: 8, maxMemoryGb: 8 },
|
|
77
|
+
// The default template; a bigger size needs a template built with --cpu-count / --memory-mb.
|
|
78
|
+
defaultSize: { vcpu: 2, memoryGb: 0.5, measured: "2026-11-06" },
|
|
50
79
|
credentials: [["E2B_API_KEY"]],
|
|
51
80
|
docs: "https://e2b.dev/docs",
|
|
52
81
|
},
|
|
@@ -62,6 +91,8 @@ const ENTRIES = [
|
|
|
62
91
|
},
|
|
63
92
|
capabilities: ["pause", "custom-image"],
|
|
64
93
|
limits: { maxVcpu: 4, maxMemoryGb: 8 },
|
|
94
|
+
// The default snapshot; resources only apply when creating from an image (image.daytona).
|
|
95
|
+
defaultSize: { vcpu: 1, memoryGb: 1, measured: "2026-11-06" },
|
|
65
96
|
credentials: [["DAYTONA_API_KEY"]],
|
|
66
97
|
docs: "https://www.daytona.io/docs",
|
|
67
98
|
},
|
|
@@ -69,11 +100,11 @@ const ENTRIES = [
|
|
|
69
100
|
id: "modal",
|
|
70
101
|
name: "Modal",
|
|
71
102
|
pricing: {
|
|
72
|
-
vcpuHour: 0.
|
|
73
|
-
gbHour: 0.
|
|
74
|
-
note: "sandbox rates, GPUs extra; region pinning x1.15-1.75",
|
|
103
|
+
vcpuHour: 0.070956,
|
|
104
|
+
gbHour: 0.024012,
|
|
105
|
+
note: "sandbox rates, per second ($0.00003942 per physical core = 2 vCPUs); GPUs extra; region pinning x1.15-1.75; Starter includes $30/mo credit",
|
|
75
106
|
source: "https://modal.com/pricing",
|
|
76
|
-
checked: "2026-11-
|
|
107
|
+
checked: "2026-11-05",
|
|
77
108
|
},
|
|
78
109
|
capabilities: ["gpu", "custom-image"],
|
|
79
110
|
limits: { maxVcpu: 64, maxMemoryGb: 256 },
|
|
@@ -86,9 +117,9 @@ const ENTRIES = [
|
|
|
86
117
|
pricing: {
|
|
87
118
|
vcpuHour: 0.128,
|
|
88
119
|
gbHour: 0.0212,
|
|
89
|
-
note: "
|
|
120
|
+
note: "iad1; active CPU, provisioned RAM in minimum 1-minute increments (2 GB/vCPU); full-CPU estimate; Hobby free within quotas, Pro $20/mo usage credit; creations $0.60/million and retained snapshots $0.08/GB-month extra",
|
|
90
121
|
source: "https://vercel.com/docs/vercel-sandbox/pricing",
|
|
91
|
-
checked: "2026-11-
|
|
122
|
+
checked: "2026-11-05",
|
|
92
123
|
},
|
|
93
124
|
capabilities: [],
|
|
94
125
|
limits: { maxVcpu: 8, maxMemoryGb: 16 },
|
|
@@ -136,7 +167,7 @@ const ENTRIES = [
|
|
|
136
167
|
source: "https://blaxel.ai/pricing",
|
|
137
168
|
checked: "2026-11-04",
|
|
138
169
|
},
|
|
139
|
-
capabilities: ["
|
|
170
|
+
capabilities: ["custom-image"],
|
|
140
171
|
// Self-serve caps are per-tier and not published; these are conservative.
|
|
141
172
|
limits: { maxVcpu: 8, maxMemoryGb: 16 },
|
|
142
173
|
credentials: [["BL_API_KEY", "BL_WORKSPACE"]],
|
|
@@ -194,11 +225,12 @@ ENTRIES.push({
|
|
|
194
225
|
pricing: {
|
|
195
226
|
vcpuHour: 0.0525,
|
|
196
227
|
gbHour: 0,
|
|
197
|
-
note: "$0.105/h per 2 vCPU
|
|
228
|
+
note: "standalone reserved size, per second: $0.105/h per 2 vCPU / 4 GiB unit; stopped CPU/RAM free, retained disk separate; Personal from $15/mo (up to 16 vCPU / 32 GiB), Work $75/mo (32 / 64 without approval)",
|
|
198
229
|
source: "https://exe.dev/docs/standalone-vms.md",
|
|
199
|
-
checked: "2026-11-
|
|
230
|
+
checked: "2026-11-05",
|
|
200
231
|
},
|
|
201
232
|
capabilities: ["custom-image"],
|
|
233
|
+
// 16 / 32 is the biggest Personal plan; Work allows 32 / 64, but the router can't tell which plan you have.
|
|
202
234
|
limits: { maxVcpu: 16, maxMemoryGb: 32 },
|
|
203
235
|
credentials: [["EXE_TOKEN"]],
|
|
204
236
|
docs: "https://exe.dev/docs/https-api.md",
|
|
@@ -237,16 +269,342 @@ ENTRIES.push({
|
|
|
237
269
|
pricing: {
|
|
238
270
|
vcpuHour: 0.072,
|
|
239
271
|
gbHour: 0.009,
|
|
240
|
-
note: "
|
|
272
|
+
note: "10 ms billing on active CPU and allocated instance memory; full-CPU estimate excludes allocated disk ($0.000252/GB-h), Worker and Durable Objects charges; needs Workers Paid ($5/mo) and bridges/cloudflare",
|
|
241
273
|
source: "https://developers.cloudflare.com/containers/platform/pricing/",
|
|
242
|
-
checked: "2026-11-
|
|
274
|
+
checked: "2026-11-05",
|
|
243
275
|
},
|
|
244
276
|
capabilities: [],
|
|
245
277
|
limits: { maxVcpu: 4, maxMemoryGb: 12 },
|
|
246
278
|
credentials: [["CLOUDFLARE_SANDBOX_URL", "CLOUDFLARE_SANDBOX_TOKEN"]],
|
|
247
279
|
docs: "https://developers.cloudflare.com/sandbox/",
|
|
248
280
|
});
|
|
249
|
-
|
|
281
|
+
ENTRIES.push({
|
|
282
|
+
id: "agentcore",
|
|
283
|
+
name: "Amazon Bedrock AgentCore Code Interpreter",
|
|
284
|
+
pricing: {
|
|
285
|
+
vcpuHour: 0.0895,
|
|
286
|
+
gbHour: 0.00945,
|
|
287
|
+
note: "per second; CPU billed on actual use (I/O wait free), memory on peak; fixed 2 vCPU / 8 GB session, this is the 100%-CPU price",
|
|
288
|
+
source: "https://aws.amazon.com/bedrock/agentcore/pricing/",
|
|
289
|
+
checked: "2026-11-04",
|
|
290
|
+
},
|
|
291
|
+
capabilities: [],
|
|
292
|
+
limits: { maxVcpu: 2, maxMemoryGb: 8 },
|
|
293
|
+
credentials: [
|
|
294
|
+
["AGENTCORE_CODE_INTERPRETER_ID", "AWS_REGION", "AWS_ACCESS_KEY_ID", "AWS_SECRET_ACCESS_KEY"],
|
|
295
|
+
["AGENTCORE_CODE_INTERPRETER_ID", "AWS_REGION", "AWS_PROFILE"],
|
|
296
|
+
],
|
|
297
|
+
docs: "https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/code-interpreter-api-reference-examples.html",
|
|
298
|
+
}, {
|
|
299
|
+
id: "azure",
|
|
300
|
+
name: "Azure Container Apps dynamic sessions",
|
|
301
|
+
pricing: {
|
|
302
|
+
vcpuHour: 0.03,
|
|
303
|
+
gbHour: 0,
|
|
304
|
+
note: "flat $0.03 per session-hour (built-in Shell pools), billed per allocated session in 1-hour increments, East US; needs a session pool you create once",
|
|
305
|
+
source: "https://learn.microsoft.com/en-us/azure/container-apps/billing#dynamic-sessions",
|
|
306
|
+
checked: "2026-11-04",
|
|
307
|
+
},
|
|
308
|
+
capabilities: [],
|
|
309
|
+
// Per-session size isn't published; placeholder until measured with nproc / free.
|
|
310
|
+
limits: { maxVcpu: 1, maxMemoryGb: 2 },
|
|
311
|
+
credentials: [
|
|
312
|
+
["AZURE_SESSIONS_POOL_ENDPOINT", "AZURE_SESSIONS_TOKEN"],
|
|
313
|
+
["AZURE_SESSIONS_POOL_ENDPOINT", "AZURE_TENANT_ID", "AZURE_CLIENT_ID", "AZURE_CLIENT_SECRET"],
|
|
314
|
+
],
|
|
315
|
+
docs: "https://learn.microsoft.com/en-us/azure/container-apps/sessions-tutorial-shell",
|
|
316
|
+
}, {
|
|
317
|
+
id: "lambda",
|
|
318
|
+
name: "AWS Lambda MicroVMs",
|
|
319
|
+
pricing: {
|
|
320
|
+
vcpuHour: 0.09969984,
|
|
321
|
+
gbHour: 0.01320012,
|
|
322
|
+
note: "us-east-1 ARM; billed on the image's baseline size (2 GB per vCPU) while running, per-second burst up to 4x; suspended VMs pay snapshot storage; needs a MicroVM image you build once",
|
|
323
|
+
source: "https://aws.amazon.com/lambda/pricing/",
|
|
324
|
+
checked: "2026-11-05",
|
|
325
|
+
},
|
|
326
|
+
capabilities: ["pause", "custom-image"],
|
|
327
|
+
limits: { maxVcpu: 4, maxMemoryGb: 8 },
|
|
328
|
+
credentials: [
|
|
329
|
+
["AWS_REGION", "LAMBDA_MICROVM_IMAGE", "AWS_ACCESS_KEY_ID", "AWS_SECRET_ACCESS_KEY"],
|
|
330
|
+
["AWS_REGION", "LAMBDA_MICROVM_IMAGE", "AWS_PROFILE"],
|
|
331
|
+
],
|
|
332
|
+
docs: "https://docs.aws.amazon.com/lambda/latest/dg/lambda-microvms-guide.html",
|
|
333
|
+
}, {
|
|
334
|
+
id: "agent37",
|
|
335
|
+
name: "Agent37",
|
|
336
|
+
pricing: {
|
|
337
|
+
vcpuHour: 0.8 / 730,
|
|
338
|
+
gbHour: 0.7 / 730,
|
|
339
|
+
note: "whole-minute billing: monthly shape total / 730 / 60; running estimate includes default disk (2 vCPU / 4 GB / 4 GB disk = $4.76/mo); sleeping/stopped disk $0.09/GB-mo; gVisor; $5 minimum top-up, wallet must hold one running day",
|
|
340
|
+
source: "https://www.agent37.com/docs/agents-api/billing",
|
|
341
|
+
checked: "2026-11-05",
|
|
342
|
+
},
|
|
343
|
+
capabilities: ["pause", "custom-image"],
|
|
344
|
+
limits: { maxVcpu: 4, maxMemoryGb: 32 },
|
|
345
|
+
credentials: [["AGENT37_API_KEY"]],
|
|
346
|
+
docs: "https://www.agent37.com/docs/agents-api/overview",
|
|
347
|
+
}, {
|
|
348
|
+
id: "alibaba",
|
|
349
|
+
name: "Alibaba Cloud Agent Sandbox",
|
|
350
|
+
pricing: {
|
|
351
|
+
vcpuHour: 0.017856,
|
|
352
|
+
gbHour: 0.008928,
|
|
353
|
+
note: "per second; Default QoS, Hong Kong and regions outside mainland China; disk separately $0.00025308/GiB-h; code-interpreter-v1 template is 2 vCPU / 2 GiB with 10 GiB disk (E2B-compatible API)",
|
|
354
|
+
source: "https://www.alibabacloud.com/help/en/agent-sandbox/product-overview/billing-overview",
|
|
355
|
+
checked: "2026-11-05",
|
|
356
|
+
},
|
|
357
|
+
capabilities: ["custom-image"],
|
|
358
|
+
// No published maximum; the default template is 2 vCPU / 2 GB, so bigger requests go elsewhere.
|
|
359
|
+
limits: { maxVcpu: 2, maxMemoryGb: 2 },
|
|
360
|
+
credentials: [["ALIBABA_SANDBOX_API_KEY"]],
|
|
361
|
+
docs: "https://www.alibabacloud.com/help/en/agent-sandbox/e2b-sdk-integration-parameter-description",
|
|
362
|
+
}, {
|
|
363
|
+
id: "beam",
|
|
364
|
+
name: "Beam",
|
|
365
|
+
pricing: {
|
|
366
|
+
vcpuHour: 0.05,
|
|
367
|
+
gbHour: 0.01,
|
|
368
|
+
note: "per second, Performance tier (sandbox default); Developer plan $20/mo incl. $20 credits; GPUs billed separately",
|
|
369
|
+
source: "https://www.beam.cloud/pricing",
|
|
370
|
+
checked: "2026-11-04",
|
|
371
|
+
},
|
|
372
|
+
capabilities: ["custom-image"],
|
|
373
|
+
// Not documented per sandbox: 30 is the Developer plan's concurrent vCPU cap.
|
|
374
|
+
limits: { maxVcpu: 30, maxMemoryGb: 64 },
|
|
375
|
+
credentials: [["BEAM_TOKEN", "BEAM_WORKSPACE_ID"]],
|
|
376
|
+
docs: "https://docs.beam.cloud/v2/reference/ts-sdk",
|
|
377
|
+
}, {
|
|
378
|
+
id: "codesandbox",
|
|
379
|
+
name: "CodeSandbox SDK (Together)",
|
|
380
|
+
pricing: {
|
|
381
|
+
vcpuHour: 0.0743,
|
|
382
|
+
gbHour: 0,
|
|
383
|
+
note: "fixed tiers: Pico 2 vCPU / 1 GB $0.0743/h, Nano 2 / 4 $0.1486/h, up to 64 / 128 $4.7552/h; credits $0.01486, billed per started minute; Build free, 10 concurrent; Scale $170/mo incl. 1,100 credits",
|
|
384
|
+
source: "https://docs.together.ai/docs/together-code-sandbox-legacy",
|
|
385
|
+
checked: "2026-11-05",
|
|
386
|
+
},
|
|
387
|
+
capabilities: ["pause", "custom-image"],
|
|
388
|
+
limits: { maxVcpu: 64, maxMemoryGb: 128 },
|
|
389
|
+
credentials: [["CSB_API_KEY"]],
|
|
390
|
+
docs: "https://codesandbox.io/docs/sdk",
|
|
391
|
+
}, {
|
|
392
|
+
id: "superserve",
|
|
393
|
+
name: "Superserve",
|
|
394
|
+
pricing: {
|
|
395
|
+
vcpuHour: 0.0504,
|
|
396
|
+
gbHour: 0.0162,
|
|
397
|
+
note: "per second active; superserve/base fixed at 2 vCPU / 4 GiB / 8 GiB disk; retained storage $0.000108/GiB-h (shared template plus changed blocks); Developer $20/mo incl. $20, max 4/16 with team templates; recurring Free allowance not published on pricing page",
|
|
398
|
+
source: "https://superserve.ai/pricing",
|
|
399
|
+
checked: "2026-11-05",
|
|
400
|
+
},
|
|
401
|
+
capabilities: ["pause", "custom-image"],
|
|
402
|
+
limits: { maxVcpu: 2, maxMemoryGb: 4 },
|
|
403
|
+
credentials: [["SUPERSERVE_API_KEY"]],
|
|
404
|
+
docs: "https://docs.superserve.ai",
|
|
405
|
+
}, {
|
|
406
|
+
id: "sail",
|
|
407
|
+
name: "Sailboxes (Sail Research)",
|
|
408
|
+
pricing: {
|
|
409
|
+
vcpuHour: 0.015,
|
|
410
|
+
gbHour: 0.008,
|
|
411
|
+
note: "per second on what the box uses (CPU time, RAM it holds, disk $0.0007/GiB-h), billed per minute; RAM counts the VM's file cache, up to the 16 GiB minimum limit, so file-heavy work can hold more than you asked for; paused/sleeping free; creation $0.01 at 2-4 vCPU on the free plan ($5/mo credit with a card), waived on Pro $250/mo",
|
|
412
|
+
source: "https://docs.sailresearch.com/sailboxes-pricing.md",
|
|
413
|
+
checked: "2026-11-06",
|
|
414
|
+
},
|
|
415
|
+
capabilities: ["pause"],
|
|
416
|
+
limits: { maxVcpu: 64, maxMemoryGb: 512 },
|
|
417
|
+
credentials: [["SAIL_API_KEY"]],
|
|
418
|
+
docs: "https://docs.sailresearch.com/sailboxes.md",
|
|
419
|
+
}, {
|
|
420
|
+
id: "openscale",
|
|
421
|
+
name: "OpenScale Sandboxes",
|
|
422
|
+
pricing: {
|
|
423
|
+
vcpuHour: 0.0065,
|
|
424
|
+
gbHour: 0.001,
|
|
425
|
+
note: "per second on allocated size; no platform fee or minimum; paused = free; size comes from the template (E2B-compatible API); Singapore only; needs a pay-as-you-go key",
|
|
426
|
+
source: "https://openscale.so/sandboxes",
|
|
427
|
+
checked: "2026-11-05",
|
|
428
|
+
},
|
|
429
|
+
capabilities: ["pause", "custom-image"],
|
|
430
|
+
limits: { maxVcpu: 8, maxMemoryGb: 16 },
|
|
431
|
+
// The "base" template; size comes from the template.
|
|
432
|
+
defaultSize: { vcpu: 2, memoryGb: 1, measured: "2026-11-06" },
|
|
433
|
+
credentials: [["OPENSCALE_API_KEY"]],
|
|
434
|
+
docs: "https://openscale.so/sandboxes",
|
|
435
|
+
}, {
|
|
436
|
+
id: "dedalus",
|
|
437
|
+
name: "Dedalus Machines",
|
|
438
|
+
pricing: {
|
|
439
|
+
vcpuHour: 0.04536,
|
|
440
|
+
gbHour: 0.01458,
|
|
441
|
+
note: "per second while awake; sleeping machines bill storage only (10 GiB included on Hobby, 20 on Pro); Hobby plan max 4 vCPU / 16 GiB; private beta",
|
|
442
|
+
source: "https://docs.dedaluslabs.ai/dcs/dm/pricing",
|
|
443
|
+
checked: "2026-11-05",
|
|
444
|
+
},
|
|
445
|
+
capabilities: ["pause"],
|
|
446
|
+
limits: { maxVcpu: 16, maxMemoryGb: 64 },
|
|
447
|
+
credentials: [["DEDALUS_API_KEY"]],
|
|
448
|
+
docs: "https://docs.dedaluslabs.ai/dcs/dm/quickstart",
|
|
449
|
+
access: { status: "waitlist", note: "private beta: your organization has to be admitted before keys work", checked: "2026-11-05" },
|
|
450
|
+
}, {
|
|
451
|
+
id: "deno",
|
|
452
|
+
name: "Deno Sandbox",
|
|
453
|
+
pricing: {
|
|
454
|
+
vcpuHour: 0.1,
|
|
455
|
+
gbHour: 0.025,
|
|
456
|
+
note: "billed on CPU time, not wall clock (estimate assumes both vCPUs busy); fixed 2 vCPU, 0.75-4 GB, max 30 min lifetime; needs a paid Deno Deploy plan",
|
|
457
|
+
source: "https://deno.com/sandbox",
|
|
458
|
+
checked: "2026-11-04",
|
|
459
|
+
},
|
|
460
|
+
capabilities: ["custom-image"],
|
|
461
|
+
limits: { maxVcpu: 2, maxMemoryGb: 4 },
|
|
462
|
+
credentials: [["DENO_DEPLOY_TOKEN"]],
|
|
463
|
+
docs: "https://docs.deno.com/sandbox/",
|
|
464
|
+
}, {
|
|
465
|
+
id: "freestyle",
|
|
466
|
+
name: "Freestyle",
|
|
467
|
+
pricing: {
|
|
468
|
+
vcpuHour: 0.04032,
|
|
469
|
+
gbHour: 0.0129,
|
|
470
|
+
note: "per second on allocated fixed snapshot size; estimate includes disk at $0.000086/GiB-h; free monthly 200 vCPU-h, 400 GiB-h RAM, 60,000 GiB-h disk; Hobby $50/mo incl. $50 (max 8/16), Pro $500 (max 32/64); paused storage only",
|
|
471
|
+
source: "https://www.freestyle.sh/docs/vms/pricing-and-limits",
|
|
472
|
+
checked: "2026-11-05",
|
|
473
|
+
},
|
|
474
|
+
capabilities: ["pause", "custom-image"],
|
|
475
|
+
limits: { maxVcpu: 32, maxMemoryGb: 64 },
|
|
476
|
+
credentials: [["FREESTYLE_API_KEY"]],
|
|
477
|
+
docs: "https://www.freestyle.sh/docs/vms",
|
|
478
|
+
}, {
|
|
479
|
+
id: "instabox",
|
|
480
|
+
name: "InstaBox",
|
|
481
|
+
pricing: {
|
|
482
|
+
vcpuHour: 0.004,
|
|
483
|
+
gbHour: 0.00225,
|
|
484
|
+
note: "per second while running on fixed sizes (2/4, 4/8, 8/16); paused or stopped boxes bill only /data beyond the included disk ($0.00011/GiB-h); Pro $20/mo includes $20 credits; free plan: 1 box at 4/8",
|
|
485
|
+
source: "https://instabox.sh/docs/pricing.md",
|
|
486
|
+
checked: "2026-11-05",
|
|
487
|
+
},
|
|
488
|
+
capabilities: ["pause", "custom-image"],
|
|
489
|
+
limits: { maxVcpu: 8, maxMemoryGb: 16 },
|
|
490
|
+
credentials: [["INSTABOX_API_KEY"]],
|
|
491
|
+
docs: "https://instabox.sh/docs/api.md",
|
|
492
|
+
access: { status: "waitlist", note: "new accounts go on a waitlist before they can create boxes or keys", checked: "2026-11-05" },
|
|
493
|
+
}, {
|
|
494
|
+
id: "koyeb",
|
|
495
|
+
name: "Koyeb Sandboxes",
|
|
496
|
+
pricing: {
|
|
497
|
+
vcpuHour: 0.0144,
|
|
498
|
+
gbHour: 0,
|
|
499
|
+
note: "per second; fixed Standard instance sizes (1 vCPU + 1 GB = $0.0144/h); sandboxes need a paid plan (Pro $29/mo); public preview",
|
|
500
|
+
source: "https://www.koyeb.com/docs/reference/instances",
|
|
501
|
+
checked: "2026-11-04",
|
|
502
|
+
},
|
|
503
|
+
capabilities: ["custom-image"],
|
|
504
|
+
limits: { maxVcpu: 40, maxMemoryGb: 128 },
|
|
505
|
+
credentials: [["KOYEB_API_TOKEN"]],
|
|
506
|
+
docs: "https://www.koyeb.com/docs/sandboxes",
|
|
507
|
+
access: {
|
|
508
|
+
status: "closed",
|
|
509
|
+
note: "Koyeb is joining Mistral; a new account's dashboard only shows that notice, with no way to create sandboxes or tokens. Existing accounts are unaffected",
|
|
510
|
+
checked: "2026-11-05",
|
|
511
|
+
},
|
|
512
|
+
}, {
|
|
513
|
+
id: "langsmith",
|
|
514
|
+
name: "LangSmith Sandboxes",
|
|
515
|
+
pricing: {
|
|
516
|
+
vcpuHour: 0.0576,
|
|
517
|
+
gbHour: 0.01845,
|
|
518
|
+
note: "per second; memory must be 2 to 6 GiB per vCPU; storage $0.000123/GiB-h; 8 LSU ($8) of sandbox usage a month included; Developer plan max 10 sandboxes",
|
|
519
|
+
source: "https://www.langchain.com/pricing",
|
|
520
|
+
checked: "2026-11-05",
|
|
521
|
+
},
|
|
522
|
+
capabilities: ["pause", "custom-image"],
|
|
523
|
+
// Not published; 16 vCPU / 96 GiB stays inside the 6 GiB per vCPU band. Real runs will tell.
|
|
524
|
+
limits: { maxVcpu: 16, maxMemoryGb: 96 },
|
|
525
|
+
credentials: [["LANGSMITH_API_KEY"]],
|
|
526
|
+
docs: "https://docs.langchain.com/langsmith/sandboxes",
|
|
527
|
+
}, {
|
|
528
|
+
id: "novita",
|
|
529
|
+
name: "Novita AI Agent Sandbox",
|
|
530
|
+
pricing: {
|
|
531
|
+
vcpuHour: 0.03528,
|
|
532
|
+
gbHour: 0.01152,
|
|
533
|
+
note: "per second ($0.0000098/vCPU/s, $0.0000032/GiB/s); size comes from the template; paused = storage only",
|
|
534
|
+
source: "https://docs.novita.ai/guides/sandbox-pricing",
|
|
535
|
+
checked: "2026-11-04",
|
|
536
|
+
},
|
|
537
|
+
capabilities: ["pause", "custom-image"],
|
|
538
|
+
limits: { maxVcpu: 8, maxMemoryGb: 8 },
|
|
539
|
+
credentials: [["NOVITA_API_KEY"]],
|
|
540
|
+
docs: "https://docs.novita.ai/guides/sandbox-overview",
|
|
541
|
+
}, {
|
|
542
|
+
id: "upstash",
|
|
543
|
+
name: "Upstash Box",
|
|
544
|
+
pricing: {
|
|
545
|
+
vcpuHour: 0.1,
|
|
546
|
+
gbHour: 0,
|
|
547
|
+
note: "billed per active CPU core-hour only (memory and idle time free); estimate assumes every core of the box busy; fixed sizes 2/4, 4/8, 8/16",
|
|
548
|
+
source: "https://upstash.com/pricing/box",
|
|
549
|
+
checked: "2026-11-04",
|
|
550
|
+
},
|
|
551
|
+
capabilities: [],
|
|
552
|
+
limits: { maxVcpu: 8, maxMemoryGb: 16 },
|
|
553
|
+
credentials: [["UPSTASH_BOX_API_KEY"]],
|
|
554
|
+
docs: "https://upstash.com/docs/box/overall/ephemeral-box",
|
|
555
|
+
});
|
|
556
|
+
/**
|
|
557
|
+
* How each provider bills, and the monthly plan it needs before the API will create sandboxes.
|
|
558
|
+
* Every provider must be listed (the Record type checks it). Plan fees come from each pricing page,
|
|
559
|
+
* checked 2026-11-06; prepaid top-ups that turn into usage aren't fees, so they don't count.
|
|
560
|
+
*/
|
|
561
|
+
const P = "2026-11-06";
|
|
562
|
+
const BILLING = {
|
|
563
|
+
docker: { billing: "allocated" },
|
|
564
|
+
agent37: { billing: "allocated" },
|
|
565
|
+
agentcore: { billing: "active-cpu" },
|
|
566
|
+
alibaba: { billing: "allocated" },
|
|
567
|
+
azure: { billing: "allocated" },
|
|
568
|
+
beam: { billing: "allocated", plan: { usdMonth: 20, credited: true, note: "Developer plan; no free plan", checked: P } },
|
|
569
|
+
blaxel: { billing: "allocated" },
|
|
570
|
+
boat: { billing: "allocated", plan: { usdMonth: 20, credited: true, note: "plan paid back as VM time; 7-day trial needs a card", checked: P } },
|
|
571
|
+
cloudflare: {
|
|
572
|
+
billing: "active-cpu",
|
|
573
|
+
plan: { usdMonth: 5, credited: false, note: "Workers Paid; includes usage allowances, not credit", checked: P },
|
|
574
|
+
},
|
|
575
|
+
codesandbox: { billing: "allocated" },
|
|
576
|
+
daytona: { billing: "allocated" },
|
|
577
|
+
dedalus: { billing: "allocated" },
|
|
578
|
+
deno: {
|
|
579
|
+
billing: "active-cpu",
|
|
580
|
+
plan: { usdMonth: 20, credited: false, note: "the free Deno Deploy plan has no sandboxes; Pro includes allowances, not credit", checked: P },
|
|
581
|
+
},
|
|
582
|
+
e2b: { billing: "allocated" },
|
|
583
|
+
exedev: { billing: "allocated", plan: { usdMonth: 15, credited: false, note: "Personal plan; VMs are metered on top; 7-day trial", checked: P } },
|
|
584
|
+
freestyle: { billing: "allocated" },
|
|
585
|
+
hopx: { billing: "allocated" },
|
|
586
|
+
instabox: { billing: "allocated" },
|
|
587
|
+
koyeb: { billing: "allocated", plan: { usdMonth: 29, credited: false, note: "sandboxes need a paid plan; Pro includes $10 of compute", checked: P } },
|
|
588
|
+
lambda: { billing: "allocated" },
|
|
589
|
+
langsmith: { billing: "allocated" },
|
|
590
|
+
maritime: { billing: "allocated", plan: { usdMonth: 20, credited: true, note: "Starter plan; no free tier; 7-day trial needs a card", checked: P } },
|
|
591
|
+
modal: { billing: "active-cpu" },
|
|
592
|
+
morph: { billing: "allocated" },
|
|
593
|
+
northflank: { billing: "allocated" },
|
|
594
|
+
novita: { billing: "allocated" },
|
|
595
|
+
openscale: { billing: "allocated" },
|
|
596
|
+
runloop: { billing: "allocated" },
|
|
597
|
+
sprites: { billing: "active-cpu" },
|
|
598
|
+
sail: { billing: "active-cpu" },
|
|
599
|
+
superserve: {
|
|
600
|
+
billing: "allocated",
|
|
601
|
+
plan: { usdMonth: 20, credited: true, unclear: true, note: "Developer plan; the page offers a free start but doesn't say what it includes", checked: P },
|
|
602
|
+
},
|
|
603
|
+
tensorlake: { billing: "active-cpu" },
|
|
604
|
+
upstash: { billing: "active-cpu" },
|
|
605
|
+
vercel: { billing: "active-cpu" },
|
|
606
|
+
};
|
|
607
|
+
export const CATALOG = ENTRIES.map((e) => ({ ...e, ...BILLING[e.id] })).sort((a, b) => a.name.localeCompare(b.name));
|
|
250
608
|
/** Cloudflare only rents fixed instance types: https://developers.cloudflare.com/containers/platform/limits/ */
|
|
251
609
|
export const CLOUDFLARE_INSTANCES = [
|
|
252
610
|
{ name: "lite", vcpu: 1 / 16, memoryGb: 0.25 },
|
|
@@ -256,6 +614,29 @@ export const CLOUDFLARE_INSTANCES = [
|
|
|
256
614
|
{ name: "standard-3", vcpu: 2, memoryGb: 8 },
|
|
257
615
|
{ name: "standard-4", vcpu: 4, memoryGb: 12 },
|
|
258
616
|
];
|
|
617
|
+
/** CodeSandbox VM tiers: https://docs.together.ai/docs/together-code-sandbox-legacy (Pico supports 2 vCPU / 1 GB). */
|
|
618
|
+
export const CODESANDBOX_TIERS = [
|
|
619
|
+
{ name: "Pico", vcpu: 2, memoryGb: 1, usdHour: 0.0743 },
|
|
620
|
+
{ name: "Nano", vcpu: 2, memoryGb: 4, usdHour: 0.1486 },
|
|
621
|
+
{ name: "Micro", vcpu: 4, memoryGb: 8, usdHour: 0.2972 },
|
|
622
|
+
{ name: "Small", vcpu: 8, memoryGb: 16, usdHour: 0.5944 },
|
|
623
|
+
{ name: "Medium", vcpu: 16, memoryGb: 32, usdHour: 1.1888 },
|
|
624
|
+
{ name: "Large", vcpu: 32, memoryGb: 64, usdHour: 2.3776 },
|
|
625
|
+
{ name: "XLarge", vcpu: 64, memoryGb: 128, usdHour: 4.7552 },
|
|
626
|
+
];
|
|
627
|
+
/** Smallest tier with at least the requested vCPUs and memory (the largest if nothing fits). */
|
|
628
|
+
export function codesandboxTier(vcpu, memoryGb) {
|
|
629
|
+
return CODESANDBOX_TIERS.find((t) => t.vcpu >= vcpu && t.memoryGb >= memoryGb) ?? CODESANDBOX_TIERS[CODESANDBOX_TIERS.length - 1];
|
|
630
|
+
}
|
|
631
|
+
/** Upstash Box sizes (https://upstash.com/docs/box/overall/how-it-works.md#box-size). */
|
|
632
|
+
export const UPSTASH_SIZES = [
|
|
633
|
+
{ size: "small", vcpu: 2, memoryGb: 4 },
|
|
634
|
+
{ size: "medium", vcpu: 4, memoryGb: 8 },
|
|
635
|
+
{ size: "large", vcpu: 8, memoryGb: 16 },
|
|
636
|
+
];
|
|
637
|
+
export function upstashSize(vcpu, memoryGb) {
|
|
638
|
+
return UPSTASH_SIZES.find((s) => s.vcpu >= vcpu && s.memoryGb >= memoryGb) ?? UPSTASH_SIZES[UPSTASH_SIZES.length - 1];
|
|
639
|
+
}
|
|
259
640
|
/** Boat's fixed machine sizes and hourly prices: https://docs.boat.dev/machines.md */
|
|
260
641
|
export const BOAT_SIZES = [
|
|
261
642
|
{ type: "small", vcpu: 2, memoryGb: 4, usdHour: 0.018 },
|
|
@@ -275,8 +656,21 @@ export function info(id) {
|
|
|
275
656
|
export const DEFAULT_VCPU = 2;
|
|
276
657
|
export const DEFAULT_MEMORY_GB = 4;
|
|
277
658
|
/** Estimated USD per hour for this spec on this provider (list price, while running). */
|
|
659
|
+
/** The size the sandbox will really have when it's fixed by the default image, else null. */
|
|
660
|
+
export function fixedSize(id, spec = {}) {
|
|
661
|
+
const d = info(id).defaultSize;
|
|
662
|
+
return d && !spec.image?.[id] ? { vcpu: d.vcpu, memoryGb: d.memoryGb } : null;
|
|
663
|
+
}
|
|
664
|
+
/** A spec this provider can take as-is: its default size if it has one, else the router default. */
|
|
665
|
+
export function fittingSpec(id) {
|
|
666
|
+
return fixedSize(id) ?? { vcpu: DEFAULT_VCPU, memoryGb: DEFAULT_MEMORY_GB };
|
|
667
|
+
}
|
|
278
668
|
export function hourlyCost(id, spec = {}) {
|
|
279
669
|
const { pricing } = info(id);
|
|
670
|
+
// You get, and pay for, the default image's size whatever you asked for.
|
|
671
|
+
const fixed = fixedSize(id, spec);
|
|
672
|
+
if (fixed)
|
|
673
|
+
return fixed.vcpu * pricing.vcpuHour + fixed.memoryGb * pricing.gbHour;
|
|
280
674
|
const vcpu = spec.vcpu ?? DEFAULT_VCPU;
|
|
281
675
|
let mem = spec.memoryGb ?? DEFAULT_MEMORY_GB;
|
|
282
676
|
// Vercel fixes memory at 2 GB per vCPU.
|
|
@@ -298,6 +692,42 @@ export function hourlyCost(id, spec = {}) {
|
|
|
298
692
|
const t = cloudflareInstance(vcpu, mem);
|
|
299
693
|
return t.vcpu * pricing.vcpuHour + t.memoryGb * pricing.gbHour;
|
|
300
694
|
}
|
|
695
|
+
// Azure bills a flat rate per allocated session.
|
|
696
|
+
if (id === "azure")
|
|
697
|
+
return pricing.vcpuHour;
|
|
698
|
+
// Lambda MicroVMs bill the smallest baseline image size that fits (2 GB per vCPU).
|
|
699
|
+
if (id === "lambda") {
|
|
700
|
+
const size = [0.5, 1, 2, 4, 8].find((s) => s >= Math.max(mem, vcpu * 2)) ?? 8;
|
|
701
|
+
return size * pricing.gbHour + (size / 2) * pricing.vcpuHour;
|
|
702
|
+
}
|
|
703
|
+
// Superserve system templates are a fixed 2 vCPU / 4 GiB, billed whole.
|
|
704
|
+
if (id === "superserve")
|
|
705
|
+
return 2 * pricing.vcpuHour + 4 * pricing.gbHour;
|
|
706
|
+
// InstaBox bills the fixed size that fits.
|
|
707
|
+
if (id === "instabox") {
|
|
708
|
+
const s = instaboxSize(vcpu, mem) ?? INSTABOX_SIZES[INSTABOX_SIZES.length - 1];
|
|
709
|
+
return s.vcpu * pricing.vcpuHour + s.memoryGb * pricing.gbHour;
|
|
710
|
+
}
|
|
711
|
+
// Agent37 publishes total running shapes per 730-hour month, including their default disk.
|
|
712
|
+
if (id === "agent37")
|
|
713
|
+
return (agent37Shape(vcpu, mem) ?? AGENT37_SHAPES[AGENT37_SHAPES.length - 1]).usdMonth / 730;
|
|
714
|
+
if (id === "codesandbox")
|
|
715
|
+
return codesandboxTier(vcpu, mem).usdHour;
|
|
716
|
+
if (id === "koyeb")
|
|
717
|
+
return (koyebInstance(vcpu, mem) ?? KOYEB_INSTANCES[KOYEB_INSTANCES.length - 1]).usdHour;
|
|
718
|
+
if (id === "freestyle")
|
|
719
|
+
return (freestyleSize(vcpu, mem) ?? FREESTYLE_SIZES[FREESTYLE_SIZES.length - 1]).usdHour;
|
|
720
|
+
// Upstash bills active core-hours on the box size that fits; this assumes every core is busy.
|
|
721
|
+
if (id === "upstash")
|
|
722
|
+
return upstashSize(vcpu, mem).vcpu * pricing.vcpuHour;
|
|
723
|
+
// Deno bills CPU time on a fixed 2 vCPU box, with at least 768 MB of memory.
|
|
724
|
+
if (id === "deno")
|
|
725
|
+
return 2 * pricing.vcpuHour + Math.max(mem, 0.75) * pricing.gbHour;
|
|
726
|
+
// LangSmith runs 2 to 6 GiB per vCPU, so a request outside that band is widened.
|
|
727
|
+
if (id === "langsmith") {
|
|
728
|
+
const s = langsmithSize(vcpu, mem);
|
|
729
|
+
return s.vcpu * pricing.vcpuHour + s.memoryGb * pricing.gbHour;
|
|
730
|
+
}
|
|
301
731
|
// Morph bills whole MCUs: the larger of vCPUs and 4 GB blocks of memory.
|
|
302
732
|
if (id === "morph")
|
|
303
733
|
return Math.max(vcpu, Math.ceil(mem / 4)) * pricing.vcpuHour;
|
|
@@ -316,5 +746,10 @@ export function unfit(id, spec, require = []) {
|
|
|
316
746
|
return `max ${p.limits.maxVcpu} vCPU`;
|
|
317
747
|
if ((spec.memoryGb ?? DEFAULT_MEMORY_GB) > p.limits.maxMemoryGb)
|
|
318
748
|
return `max ${p.limits.maxMemoryGb} GB memory`;
|
|
749
|
+
// A default image's size is fixed. With no size asked for you get that size, so only a size you
|
|
750
|
+
// name can be too big for it.
|
|
751
|
+
const fixed = fixedSize(id, spec);
|
|
752
|
+
if (fixed && ((spec.vcpu ?? 0) > fixed.vcpu || (spec.memoryGb ?? 0) > fixed.memoryGb))
|
|
753
|
+
return `default image is ${fixed.vcpu} vCPU / ${fixed.memoryGb} GB; a bigger size needs image.${id}`;
|
|
319
754
|
return null;
|
|
320
755
|
}
|
package/dist/check.d.ts
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import type { Router } from "./router.js";
|
|
2
|
+
import type { ProviderId, SandboxSpec } from "./types.js";
|
|
3
|
+
/** Every step `check` runs, in order. Each provider's saved report is scored against this list. */
|
|
4
|
+
export declare const CHECK_STEPS: readonly ["create", "exec: stdout, stderr, exit code", "exec: env and cwd", "exec: UTF-8 output", "exec: streaming", "files: binary round-trip", "files: 1 MB round-trip", "files: missing file is an error", "files: visible to commands", "exec: command timeout", "exec: timed-out command was stopped", "pause and resume", "kill", "killed sandbox is gone"];
|
|
5
|
+
export type CheckStatus = "pass" | "fail" | "skip" | "info";
|
|
6
|
+
export interface CheckResult {
|
|
7
|
+
step: string;
|
|
8
|
+
status: CheckStatus;
|
|
9
|
+
ms: number;
|
|
10
|
+
detail?: string;
|
|
11
|
+
}
|
|
12
|
+
export interface CheckReport {
|
|
13
|
+
provider: ProviderId;
|
|
14
|
+
sandboxId?: string;
|
|
15
|
+
results: CheckResult[];
|
|
16
|
+
/** True when no step failed. */
|
|
17
|
+
ok: boolean;
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* One real pass over a provider: create, exec (stdout, stderr, exit code, env, cwd), streaming,
|
|
21
|
+
* a binary file round-trip, pause and resume where supported, and kill. Meant for testing an
|
|
22
|
+
* adapter against a real account; every step is recorded, and later steps still run after a
|
|
23
|
+
* failure when they can.
|
|
24
|
+
*/
|
|
25
|
+
export declare function checkProvider(router: Router, provider: ProviderId, opts?: {
|
|
26
|
+
spec?: SandboxSpec;
|
|
27
|
+
onStep?: (r: CheckResult) => void;
|
|
28
|
+
}): Promise<CheckReport>;
|