withruntime 0.12.0 → 0.16.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.
Files changed (94) hide show
  1. package/BLAXEL.md +97 -32
  2. package/COMPATIBILITY.md +120 -5
  3. package/DAYTONA.md +34 -3
  4. package/E2B.md +34 -5
  5. package/README.md +36 -3
  6. package/README.src.md +35 -2
  7. package/VERCEL.md +52 -5
  8. package/compatibility-lock.json +71 -111
  9. package/dist/billing-cli.js +8 -4
  10. package/dist/blaxel/client.d.ts +11 -0
  11. package/dist/blaxel/client.js +28 -0
  12. package/dist/blaxel/errors.d.ts +65 -0
  13. package/dist/blaxel/errors.js +114 -0
  14. package/dist/blaxel/index.d.ts +10 -3
  15. package/dist/blaxel/index.js +23 -4
  16. package/dist/blaxel/preview.d.ts +29 -4
  17. package/dist/blaxel/preview.js +79 -5
  18. package/dist/blaxel/sandbox.d.ts +1 -1
  19. package/dist/blaxel/sandbox.js +2 -1
  20. package/dist/blaxel/session.js +4 -2
  21. package/dist/cli-extras.js +2 -1
  22. package/dist/cli-words.js +1 -0
  23. package/dist/cli.d.ts +17 -2
  24. package/dist/cli.js +291 -85
  25. package/dist/client.d.ts +1 -1
  26. package/dist/credentials.d.ts +3 -0
  27. package/dist/credentials.js +15 -0
  28. package/dist/daytona/client.d.ts +4 -0
  29. package/dist/daytona/client.js +8 -3
  30. package/dist/daytona/daytona.d.ts +4 -1
  31. package/dist/daytona/daytona.js +3 -2
  32. package/dist/e2b/sandbox.d.ts +7 -6
  33. package/dist/e2b/sandbox.js +9 -12
  34. package/dist/errors.d.ts +1 -1
  35. package/dist/errors.js +1 -1
  36. package/dist/freestyle/index.d.ts +77 -5
  37. package/dist/freestyle/index.js +380 -48
  38. package/dist/identity.js +36 -18
  39. package/dist/index.d.ts +4 -3
  40. package/dist/machine.d.ts +39 -13
  41. package/dist/machine.js +72 -25
  42. package/dist/mcp.js +157 -20
  43. package/dist/modal/index.d.ts +15 -0
  44. package/dist/modal/index.js +35 -7
  45. package/dist/morph/index.d.ts +255 -0
  46. package/dist/morph/index.js +641 -0
  47. package/dist/network-cli.js +2 -2
  48. package/dist/product-names.d.ts +2 -2
  49. package/dist/product-names.js +2 -2
  50. package/dist/products/api-keys.d.ts +73 -0
  51. package/dist/products/api-keys.js +23 -0
  52. package/dist/products/apps.d.ts +12 -31
  53. package/dist/products/apps.js +8 -113
  54. package/dist/products/balancers.d.ts +87 -0
  55. package/dist/products/balancers.js +8 -0
  56. package/dist/products/builds.d.ts +30 -0
  57. package/dist/products/builds.js +6 -0
  58. package/dist/products/index.d.ts +2 -0
  59. package/dist/products/index.js +2 -0
  60. package/dist/products/jobs.d.ts +2 -2
  61. package/dist/products/jobs.js +1 -1
  62. package/dist/products/limits.d.ts +16 -2
  63. package/dist/products/limits.js +2 -2
  64. package/dist/products/mcp.d.ts +5 -0
  65. package/dist/products/network-products.d.ts +21 -3
  66. package/dist/products/network-products.js +3 -1
  67. package/dist/products/observability.d.ts +7 -2
  68. package/dist/products/previews.d.ts +6 -3
  69. package/dist/products/previews.js +1 -1
  70. package/dist/products/resources.d.ts +54 -0
  71. package/dist/products/resources.js +122 -0
  72. package/dist/products/secrets.d.ts +22 -0
  73. package/dist/products/secrets.js +8 -0
  74. package/dist/products/volumes.d.ts +3 -0
  75. package/dist/sandbox.d.ts +4 -0
  76. package/dist/sandbox.js +27 -2
  77. package/dist/snapshots.d.ts +4 -0
  78. package/dist/ssh.d.ts +35 -0
  79. package/dist/ssh.js +93 -1
  80. package/dist/transport.d.ts +14 -8
  81. package/dist/transport.js +70 -15
  82. package/dist/types.d.ts +33 -5
  83. package/dist/vercel/command.d.ts +48 -1
  84. package/dist/vercel/command.js +237 -6
  85. package/dist/vercel/sandbox-user.js +2 -1
  86. package/dist/vercel/sandbox.d.ts +17 -3
  87. package/dist/vercel/sandbox.js +46 -3
  88. package/dist/wallet.d.ts +4 -1
  89. package/dist/wallet.js +2 -1
  90. package/package.json +7 -14
  91. package/dist/cli/logs.test.d.ts +0 -1
  92. package/dist/cli/logs.test.js +0 -272
  93. package/dist/products/logs.test.d.ts +0 -1
  94. package/dist/products/logs.test.js +0 -343
@@ -1,5 +1,5 @@
1
1
  import { ConflictError as NativeConflictError, InvalidRequestError, NotFoundError as NativeNotFoundError, RateLimitError, RuntimeError, ServiceUnavailableError, } from "../errors.js";
2
- import { all, client, CompatibilityError, create, destroy, execOptions, only, refuse, region, } from "../compat/core.js";
2
+ import { all, client, CompatibilityError, create, destroy, execOptions, only, refuse, refusal, refused, region, } from "../compat/core.js";
3
3
  import { GuestFiles } from "../compat/files.js";
4
4
  export { CompatibilityError };
5
5
  // Errors ----------------------------------------------------------------------
@@ -104,6 +104,9 @@ export class App {
104
104
  this.environmentName = environmentName;
105
105
  }
106
106
  }
107
+ refuse("Modal", "App", App, {
108
+ info: "a Runtime app is a label on its sandboxes, with no lifecycle, Functions or Servers: list them with client.sandboxes.list({ appId: app.appId })",
109
+ });
107
110
  export class AppService {
108
111
  client;
109
112
  constructor(client) {
@@ -183,9 +186,11 @@ export class VolumeService {
183
186
  }
184
187
  async fromName(name, params = {}) {
185
188
  this.client.open();
186
- only("Modal volume", params, ["createIfMissing", "environment"]);
189
+ only("Modal volume", params, ["createIfMissing", "environment", "version"]);
187
190
  if (params.environment)
188
191
  throw new CompatibilityError("Modal", "named Modal environments");
192
+ if (params.version !== undefined)
193
+ throw new CompatibilityError("Modal", "VolumeFS versions; a Runtime volume has one format, so omit version");
189
194
  const found = await this.find(name);
190
195
  if (found)
191
196
  return new Volume(found.id, name);
@@ -402,6 +407,21 @@ export class SandboxSnapshotService {
402
407
  return new SandboxSnapshot(snapshot.id);
403
408
  }
404
409
  }
410
+ // Environments ------------------------------------------------------------------
411
+ const NO_ENVIRONMENTS = "Runtime has no Modal environments: an account's sandboxes share one namespace, grouped by app name (client.apps.fromName) and tags";
412
+ /** `client.environments` (modal 0.11.1): refused, as `environment` options are. */
413
+ export class EnvironmentService {
414
+ }
415
+ refuse("Modal", "EnvironmentService", EnvironmentService, { fromName: NO_ENVIRONMENTS });
416
+ Object.defineProperty(EnvironmentService.prototype, "objects", {
417
+ configurable: true,
418
+ get() {
419
+ throw refusal("Modal", "EnvironmentService.objects", NO_ENVIRONMENTS);
420
+ },
421
+ });
422
+ export const Environment = refused("Modal", "Environment", NO_ENVIRONMENTS);
423
+ export const EnvironmentAppsService = refused("Modal", "EnvironmentAppsService", NO_ENVIRONMENTS);
424
+ export const EnvironmentObjectsService = refused("Modal", "EnvironmentObjectsService", NO_ENVIRONMENTS);
405
425
  export class ModalClient {
406
426
  runtime;
407
427
  apps;
@@ -412,6 +432,7 @@ export class ModalClient {
412
432
  cloudBucketMounts = new CloudBucketMountService();
413
433
  sandboxSnapshots;
414
434
  proxies = new ProxyService();
435
+ environments = new EnvironmentService();
415
436
  #closed = false;
416
437
  constructor(options = {}) {
417
438
  if (options.endpoint !== undefined ||
@@ -458,7 +479,7 @@ export class ModalClient {
458
479
  }
459
480
  /** The Modal SDK version whose interface this adapter implements. */
460
481
  version() {
461
- return "0.11.0";
482
+ return "0.11.1";
462
483
  }
463
484
  close() {
464
485
  // The transport owns no background connection; later calls fail as Modal's do.
@@ -619,14 +640,21 @@ export class SandboxService {
619
640
  throw new NotFoundError("Sandbox is not a Modal-compatible sandbox");
620
641
  return new Sandbox(s, new ContainerProcess(await modal(() => s.processes.get(p)), "text"), this.client);
621
642
  }
643
+ /** The running sandbox of that name; with includeTerminated, when none
644
+ * runs, the one that stopped last (modal 0.11.1). */
622
645
  async fromName(appName, name, params = {}) {
623
646
  this.client?.open();
624
- only("Modal sandbox name", params, ["environment"]);
647
+ only("Modal sandbox name", params, ["environment", "includeTerminated"]);
625
648
  if (params.environment)
626
649
  throw new CompatibilityError("Modal", ENVIRONMENTS);
627
- const s = (await all(this.runtime, "modal")).find((s) => s.info.labels["modal.app"] === appName &&
628
- s.info.labels["modal.name"] === name &&
629
- s.state === "running");
650
+ const named = (await all(this.runtime, "modal")).filter((s) => s.info.labels["modal.app"] === appName && s.info.labels["modal.name"] === name);
651
+ const ended = (s) => s.info.endedAt ?? s.info.createdAt ?? "";
652
+ const s = named.find((s) => s.state === "running") ??
653
+ (params.includeTerminated
654
+ ? named
655
+ .filter((s) => s.state === "stopped")
656
+ .sort((a, b) => ended(b).localeCompare(ended(a)))[0]
657
+ : undefined);
630
658
  if (!s)
631
659
  throw new NotFoundError(`Sandbox ${name} not found`);
632
660
  return this.fromId(s.id);
@@ -0,0 +1,255 @@
1
+ import type { Runtime } from "../client.js";
2
+ import type { Preview } from "../products/previews.js";
3
+ import { Sandbox } from "../sandbox.js";
4
+ import type { Snapshot as NativeSnapshot } from "../snapshots.js";
5
+ import { CompatibilityError, type ClientOptions, type RefusedAsync } from "../compat/core.js";
6
+ export { CompatibilityError };
7
+ /** Morph's base image; on Runtime, the default image. */
8
+ export declare const MORPH_DEFAULT_IMAGE = "morphvm-minimal";
9
+ export declare enum SnapshotStatus {
10
+ PENDING = "pending",
11
+ READY = "ready",
12
+ FAILED = "failed",
13
+ DELETING = "deleting",
14
+ DELETED = "deleted"
15
+ }
16
+ export declare enum InstanceStatus {
17
+ PENDING = "pending",
18
+ READY = "ready",
19
+ PAUSED = "paused",
20
+ SAVING = "saving",
21
+ ERROR = "error"
22
+ }
23
+ export interface ResourceSpec {
24
+ vcpus: number;
25
+ /** MiB. */
26
+ memory: number;
27
+ /** MiB. */
28
+ diskSize: number;
29
+ }
30
+ export interface SnapshotRefs {
31
+ imageId: string;
32
+ }
33
+ export interface InstanceHttpService {
34
+ name: string;
35
+ port: number;
36
+ url: string;
37
+ }
38
+ export interface InstanceNetworking {
39
+ internalIp?: string;
40
+ httpServices: InstanceHttpService[];
41
+ auth_mode?: string;
42
+ }
43
+ export interface InstanceRefs {
44
+ snapshotId: string;
45
+ imageId: string;
46
+ }
47
+ export interface InstanceExecResponse {
48
+ exit_code: number;
49
+ stdout: string;
50
+ stderr: string;
51
+ }
52
+ export interface InstanceTTL {
53
+ ttlSeconds?: number;
54
+ ttlExpireAt?: number;
55
+ ttlAction?: "stop" | "pause";
56
+ }
57
+ export interface InstanceWakeOn {
58
+ wakeOnSsh?: boolean;
59
+ wakeOnHttp?: boolean;
60
+ }
61
+ export interface ExecOptions {
62
+ /** Seconds; default 24 hours, as Morph's. */
63
+ timeout?: number;
64
+ onStdout?: (content: string) => void;
65
+ onStderr?: (content: string) => void;
66
+ }
67
+ export interface InstanceSshKey {
68
+ object: "instance_ssh_key";
69
+ private_key: string;
70
+ public_key: string;
71
+ password: string;
72
+ }
73
+ export interface MorphCloudClientOptions extends ClientOptions {
74
+ /** A Runtime key (`rtcloud_...`); a Morph key is never sent anywhere. */
75
+ apiKey?: string;
76
+ baseUrl?: string;
77
+ verbose?: boolean;
78
+ }
79
+ export type ImageListOptions = Record<string, never>;
80
+ export interface SnapshotListOptions {
81
+ digest?: string;
82
+ metadata?: Record<string, string>;
83
+ }
84
+ export interface SnapshotCreateOptions {
85
+ imageId?: string;
86
+ vcpus?: number;
87
+ memory?: number;
88
+ diskSize?: number;
89
+ digest?: string;
90
+ metadata?: Record<string, string>;
91
+ }
92
+ export interface SnapshotGetOptions {
93
+ snapshotId: string;
94
+ }
95
+ export interface InstanceListOptions {
96
+ metadata?: Record<string, string>;
97
+ }
98
+ export interface InstanceStartOptions {
99
+ snapshotId: string;
100
+ metadata?: Record<string, string>;
101
+ ttlSeconds?: number;
102
+ ttlAction?: "stop" | "pause";
103
+ /** Seconds to wait until it runs. */
104
+ timeout?: number;
105
+ }
106
+ export interface InstanceSnapshotOptions {
107
+ digest?: string;
108
+ metadata?: Record<string, string>;
109
+ }
110
+ export interface InstanceGetOptions {
111
+ instanceId: string;
112
+ }
113
+ export interface InstanceStopOptions {
114
+ instanceId: string;
115
+ }
116
+ export interface InstanceBootOptions {
117
+ snapshotId: string;
118
+ vcpus?: number;
119
+ memory?: number;
120
+ diskSize?: number;
121
+ metadata?: Record<string, string>;
122
+ ttlSeconds?: number;
123
+ ttlAction?: "stop" | "pause";
124
+ }
125
+ export interface SyncOptions {
126
+ delete?: boolean;
127
+ dryRun?: boolean;
128
+ verbose?: boolean;
129
+ respectGitignore?: boolean;
130
+ }
131
+ export declare class Image {
132
+ readonly id: string;
133
+ readonly name: string;
134
+ readonly diskSize: number;
135
+ readonly created: number;
136
+ readonly description?: string | undefined;
137
+ readonly object: "image";
138
+ constructor(id: string, name: string, diskSize: number, created: number, description?: string | undefined);
139
+ }
140
+ export declare class Snapshot {
141
+ #private;
142
+ readonly native: NativeSnapshot;
143
+ readonly id: string;
144
+ readonly object: "snapshot";
145
+ readonly created: number;
146
+ readonly status: SnapshotStatus;
147
+ readonly spec: ResourceSpec;
148
+ readonly refs: SnapshotRefs;
149
+ readonly digest?: string;
150
+ metadata?: Record<string, string>;
151
+ constructor(native: NativeSnapshot, morph: MorphCloudClient);
152
+ delete(): Promise<void>;
153
+ /** Morph's chain hash: SHA-256 of the parent's hash, a newline and the effect. */
154
+ static computeChainHash(parentChainHash: string, effectIdentifier: string): string;
155
+ /** Runs `command` on a copy of this snapshot and snapshots the result, once:
156
+ * a later setup of the same command on the same snapshot answers the
157
+ * snapshot made the first time. A command that fails throws, and the copy
158
+ * is stopped either way. */
159
+ setup(command: string): Promise<Snapshot>;
160
+ /** Adds or changes these metadata keys; the others stay. */
161
+ setMetadata(metadata: Record<string, string>): Promise<void>;
162
+ }
163
+ export declare class Instance {
164
+ #private;
165
+ readonly id: string;
166
+ readonly object: "instance";
167
+ readonly created: number;
168
+ status: InstanceStatus;
169
+ readonly spec: ResourceSpec;
170
+ readonly refs: InstanceRefs;
171
+ networking: InstanceNetworking;
172
+ ttl: InstanceTTL;
173
+ wakeOn: InstanceWakeOn;
174
+ metadata?: Record<string, string>;
175
+ readonly ssh: RefusedAsync;
176
+ readonly sshKey: RefusedAsync;
177
+ readonly sshKeyRotate: RefusedAsync;
178
+ readonly reboot: RefusedAsync;
179
+ readonly setTTL: RefusedAsync;
180
+ constructor(sandbox: Sandbox, morph: MorphCloudClient, previews?: Preview[]);
181
+ /** The Runtime sandbox behind it, for what Morph has no call for. */
182
+ get native(): Sandbox;
183
+ /** Deletes it, with its disk and memory, as Morph's stop does; its snapshots stay. */
184
+ stop(): Promise<void>;
185
+ /** Keeps memory and disk, and stops compute charges. */
186
+ pause(): Promise<void>;
187
+ resume(): Promise<void>;
188
+ /** Adds or changes these metadata keys; the others stay. */
189
+ setMetadata(metadata: Record<string, string>): Promise<void>;
190
+ /** Runtime wakes a paused sandbox on any request (an API call, SSH, a
191
+ * visit to a shared port) or on none: both values must agree. */
192
+ setWakeOn(wakeOnSsh?: boolean, wakeOnHttp?: boolean): Promise<void>;
193
+ /** Files, memory and running processes; a running instance pauses for the
194
+ * moment it takes, then runs on. */
195
+ snapshot(options?: InstanceSnapshotOptions): Promise<Snapshot>;
196
+ /** `count` running copies, with its files, memory and processes, and the
197
+ * snapshot they were started from, which is kept. */
198
+ branch(count: number): Promise<{
199
+ snapshot: Snapshot;
200
+ instances: Instance[];
201
+ }>;
202
+ /** Shares `port` at an HTTPS address. With no auth_mode, anyone with the
203
+ * address reaches it (Runtime's public preview, which needs a kept
204
+ * top-up); with auth_mode "api_key", a request needs the preview's token
205
+ * in `x-runtime-preview-token` (native.previews.get(port)). */
206
+ exposeHttpService(name: string, port: number, auth_mode?: string): Promise<InstanceHttpService>;
207
+ hideHttpService(name: string): Promise<void>;
208
+ /** A string, or a one-item array, runs in a shell; a longer array runs as
209
+ * its arguments. Output streams to onStdout and onStderr as it comes. */
210
+ exec(command: string | string[], options?: ExecOptions): Promise<InstanceExecResponse>;
211
+ /** Seconds; waits until it runs, waking it if paused. */
212
+ waitUntilReady(timeout?: number): Promise<void>;
213
+ /** Copies a local file or folder into the instance, or out of it: the
214
+ * instance's side is written `<instance id>:<path>`. Without delete, dry
215
+ * runs or .gitignore, which refuse. */
216
+ sync(source: string, dest: string, options?: SyncOptions): Promise<void>;
217
+ }
218
+ /** Morph's client, on Runtime. `new MorphCloudClient()` reads RUNTIME_API_KEY
219
+ * (or a saved login), never MORPH_API_KEY. */
220
+ export declare class MorphCloudClient {
221
+ readonly runtime: Runtime;
222
+ readonly baseUrl: string;
223
+ readonly apiKey: string;
224
+ readonly verbose: boolean;
225
+ readonly GET: RefusedAsync;
226
+ readonly POST: RefusedAsync;
227
+ readonly streamPOST: RefusedAsync;
228
+ readonly DELETE: RefusedAsync;
229
+ constructor(options?: MorphCloudClientOptions);
230
+ images: {
231
+ /** Morph's base image, which is Runtime's default image. Build others with runtime.images. */
232
+ list: (_options?: ImageListOptions) => Promise<Image[]>;
233
+ };
234
+ snapshots: {
235
+ list: (options?: SnapshotListOptions) => Promise<Snapshot[]>;
236
+ /** A bootable snapshot of an image at a size: Runtime boots a sandbox from
237
+ * the image, snapshots its disk and stops it. With a digest, a snapshot
238
+ * already made with it is answered instead. */
239
+ create: (options?: SnapshotCreateOptions) => Promise<Snapshot>;
240
+ get: (options: SnapshotGetOptions) => Promise<Snapshot>;
241
+ };
242
+ instances: {
243
+ /** Running and paused instances whose metadata match. */
244
+ list: (options?: InstanceListOptions) => Promise<Instance[]>;
245
+ /** A running copy of a snapshot: files, and memory and processes when the
246
+ * snapshot kept them. */
247
+ start: (options: InstanceStartOptions) => Promise<Instance>;
248
+ /** As start; a different vcpus or memory restarts it at that size (its
249
+ * files kept, its programs started afresh). The disk keeps the snapshot's size. */
250
+ boot: (options: InstanceBootOptions) => Promise<Instance>;
251
+ get: (options: InstanceGetOptions) => Promise<Instance>;
252
+ /** Deletes it, with its disk and memory, as Morph's stop does; its snapshots stay. */
253
+ stop: (options: InstanceStopOptions) => Promise<void>;
254
+ };
255
+ }