@magpiecloud/mags 1.7.5 → 1.8.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/bin/mags.js CHANGED
@@ -217,6 +217,7 @@ ${colors.bold}Run Options:${colors.reset}
217
217
  -w, --workspace <id> Use persistent workspace (S3 sync)
218
218
  -n, --name <name> Set job name (for easier reference)
219
219
  -p, --persistent Keep VM alive after script completes
220
+ --no-sleep Never auto-sleep this VM (requires -p)
220
221
  --base <workspace> Mount workspace read-only as base image
221
222
  -e, --ephemeral No workspace/S3 sync (fastest execution)
222
223
  -f, --file <path> Upload file(s) to VM (repeatable)
@@ -457,6 +458,7 @@ async function runJob(args) {
457
458
  let baseWorkspace = '';
458
459
  let name = '';
459
460
  let persistent = false;
461
+ let noSleep = false;
460
462
  let ephemeral = false;
461
463
  let enableUrl = false;
462
464
  let port = 8080;
@@ -481,6 +483,9 @@ async function runJob(args) {
481
483
  case '--persistent':
482
484
  persistent = true;
483
485
  break;
486
+ case '--no-sleep':
487
+ noSleep = true;
488
+ break;
484
489
  case '-e':
485
490
  case '--ephemeral':
486
491
  ephemeral = true;
@@ -522,6 +527,10 @@ async function runJob(args) {
522
527
  log('red', 'Error: Cannot use --ephemeral with --base; ephemeral VMs have no workspace support');
523
528
  process.exit(1);
524
529
  }
530
+ if (noSleep && !persistent) {
531
+ log('red', 'Error: --no-sleep requires --persistent (-p)');
532
+ process.exit(1);
533
+ }
525
534
 
526
535
  // Upload files if any
527
536
  let fileIds = [];
@@ -546,6 +555,7 @@ async function runJob(args) {
546
555
  type: 'inline',
547
556
  persistent
548
557
  };
558
+ if (noSleep) payload.no_sleep = true;
549
559
  // Only set workspace_id if not ephemeral
550
560
  if (!ephemeral && workspace) payload.workspace_id = workspace;
551
561
  if (name) payload.name = name;
@@ -579,6 +589,14 @@ async function runJob(args) {
579
589
  log('green', `Completed in ${status.script_duration_ms}ms`);
580
590
  break;
581
591
  } else if (status.status === 'running' && persistent) {
592
+ // If --url requested, wait until VM is actually assigned (vm_id populated)
593
+ if (enableUrl && !status.vm_id) {
594
+ process.stdout.write('.');
595
+ await sleep(1000);
596
+ attempt++;
597
+ continue;
598
+ }
599
+
582
600
  log('green', 'VM running');
583
601
 
584
602
  if (enableUrl && status.subdomain) {
@@ -587,7 +605,7 @@ async function runJob(args) {
587
605
  if (accessResp.success) {
588
606
  log('green', `URL: https://${status.subdomain}.apps.magpiecloud.com`);
589
607
  } else {
590
- log('yellow', 'Warning: Could not enable URL access');
608
+ log('yellow', `Warning: Could not enable URL access${accessResp.error ? ': ' + accessResp.error : ''}`);
591
609
  }
592
610
  }
593
611
  return;
@@ -1338,7 +1356,7 @@ async function main() {
1338
1356
  break;
1339
1357
  case '--version':
1340
1358
  case '-v':
1341
- console.log('mags v1.7.0');
1359
+ console.log('mags v1.8.1');
1342
1360
  process.exit(0);
1343
1361
  break;
1344
1362
  case 'new':
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@magpiecloud/mags",
3
- "version": "1.7.5",
3
+ "version": "1.8.1",
4
4
  "description": "Mags CLI - Execute scripts on Magpie's instant VM infrastructure",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "magpie-mags"
7
- version = "1.0.0"
7
+ version = "1.1.0"
8
8
  description = "Mags SDK - Execute scripts on Magpie's instant VM infrastructure"
9
9
  readme = "README.md"
10
10
  license = {text = "MIT"}
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: magpie-mags
3
- Version: 1.0.0
3
+ Version: 1.1.0
4
4
  Summary: Mags SDK - Execute scripts on Magpie's instant VM infrastructure
5
5
  Author: Magpie Cloud
6
6
  License: MIT
@@ -3,4 +3,4 @@
3
3
  from .client import Mags
4
4
 
5
5
  __all__ = ["Mags"]
6
- __version__ = "1.0.0"
6
+ __version__ = "1.1.0"
@@ -98,6 +98,7 @@ class Mags:
98
98
  workspace_id: str | None = None,
99
99
  base_workspace_id: str | None = None,
100
100
  persistent: bool = False,
101
+ no_sleep: bool = False,
101
102
  ephemeral: bool = False,
102
103
  startup_command: str | None = None,
103
104
  environment: Dict[str, str] | None = None,
@@ -111,12 +112,16 @@ class Mags:
111
112
  raise MagsError("Cannot use ephemeral with workspace_id")
112
113
  if ephemeral and persistent:
113
114
  raise MagsError("Cannot use ephemeral with persistent")
115
+ if no_sleep and not persistent:
116
+ raise MagsError("no_sleep requires persistent=True")
114
117
 
115
118
  payload = {
116
119
  "script": script,
117
120
  "type": "inline",
118
121
  "persistent": persistent,
119
122
  }
123
+ if no_sleep:
124
+ payload["no_sleep"] = True
120
125
  if name:
121
126
  payload["name"] = name
122
127
  if not ephemeral and workspace_id:
package/website/api.html CHANGED
@@ -336,6 +336,12 @@ m = Mags(api_token="your-token")
336
336
  <td>no</td>
337
337
  <td>If <code>true</code>, VM stays alive after script finishes.</td>
338
338
  </tr>
339
+ <tr>
340
+ <td><code>no_sleep</code></td>
341
+ <td>bool</td>
342
+ <td>no</td>
343
+ <td>If <code>true</code>, VM will never be auto-slept by the idle timeout. Requires <code>persistent: true</code>.</td>
344
+ </tr>
339
345
  <tr>
340
346
  <td><code>startup_command</code></td>
341
347
  <td>string</td>
@@ -3,14 +3,14 @@
3
3
  <head>
4
4
  <meta charset="utf-8" />
5
5
  <meta name="viewport" content="width=device-width, initial-scale=1" />
6
- <title>Mags - Instant Sandboxes and Runtime Environments</title>
6
+ <title>Mags - Secure Cloud Sandboxes for AI Agents and Developers</title>
7
7
  <meta
8
8
  name="description"
9
- content="Mags is a CLI, Python SDK, and Node.js SDK for running scripts on isolated microVMs with persistent workspaces and optional URL access."
9
+ content="Mags gives AI agents and developers secure, isolated sandboxes that boot in milliseconds. Workspaces persist automatically to the cloud. Run code, schedule jobs, and let agents work safely."
10
10
  />
11
11
  <meta name="api-base" content="https://api.magpiecloud.com" />
12
12
  <meta name="auth-base" content="https://api.magpiecloud.com" />
13
- <link rel="stylesheet" href="styles.css?v=3" />
13
+ <link rel="stylesheet" href="styles.css?v=5" />
14
14
  <script src="env.js"></script>
15
15
  </head>
16
16
  <body>
@@ -20,7 +20,7 @@
20
20
  <div class="container nav">
21
21
  <div class="brand">
22
22
  <span class="logo">Mags</span>
23
- <span class="tag">Instant sandboxes and runtime environments</span>
23
+ <span class="tag">Secure cloud sandboxes for the AI age</span>
24
24
  </div>
25
25
  <nav class="nav-links">
26
26
  <a href="#overview">Overview</a>
@@ -42,11 +42,12 @@
42
42
  <div class="container hero-grid">
43
43
  <div class="hero-copy">
44
44
  <span class="pill">New: Python SDK</span>
45
- <h1>Run scripts in clean microVMs with persistent workspaces.</h1>
45
+ <h1>Secure sandboxes that boot in milliseconds. Your data stays.</h1>
46
46
  <p class="lead">
47
- Mags gives developers a CLI, Python SDK, and Node.js SDK for running
48
- code in isolated microVMs. Keep files and packages between runs, and
49
- expose a URL or SSH session when you need it.
47
+ Give your AI agents and scripts a safe place to run. Every sandbox is
48
+ completely isolated, boots instantly, and syncs your files to the cloud
49
+ automatically. Perfect for agents, scheduled jobs, and anything that
50
+ needs to run without risk.
50
51
  </p>
51
52
  <div class="hero-actions">
52
53
  <a class="button" href="#quickstart">Quickstart</a>
@@ -54,7 +55,7 @@
54
55
  </div>
55
56
  <div class="hero-meta">
56
57
  <span>CLI, Python, and Node.js &mdash; pick your tool.</span>
57
- <span>VMs boot in ~300ms. Workspaces persist to S3.</span>
58
+ <span>Sandboxes in ~300ms. Files persist to the cloud between runs.</span>
58
59
  </div>
59
60
  </div>
60
61
  <div class="hero-card tab-group" aria-label="Mags example">
@@ -68,7 +69,7 @@
68
69
 
69
70
  mags run -w myproject 'pip install flask'
70
71
  mags ssh myproject</code></pre>
71
- <p class="card-note">Run a script, persist a workspace, then jump in with SSH.</p>
72
+ <p class="card-note">Run a script, keep your files, then jump in with SSH.</p>
72
73
  </div>
73
74
  <div class="tab-content" data-tab="hero-python">
74
75
  <pre><code>from mags import Mags
@@ -95,7 +96,7 @@ console.log(result.logs);</code></pre>
95
96
  <div class="container">
96
97
  <div class="section-title">
97
98
  <p>Quickstart</p>
98
- <h2>Get from zero to your first run.</h2>
99
+ <h2>Three steps. Your first sandbox in under a minute.</h2>
99
100
  </div>
100
101
  <div class="tab-group">
101
102
  <div class="tab-bar">
@@ -118,7 +119,7 @@ console.log(result.logs);</code></pre>
118
119
  <article class="card" data-reveal>
119
120
  <h3>3. Run</h3>
120
121
  <pre><code>mags run 'echo Hello World'</code></pre>
121
- <p>Add <code>-w myproject</code> to persist files between runs.</p>
122
+ <p>Add <code>-w myproject</code> to keep files between runs, synced to the cloud.</p>
122
123
  </article>
123
124
  </div>
124
125
  </div>
@@ -174,7 +175,7 @@ console.log(result.status); // "completed"</code></pre>
174
175
  <div class="container">
175
176
  <div class="section-title">
176
177
  <p>Usage Patterns</p>
177
- <h2>Everything you can do with Mags.</h2>
178
+ <h2>Run agents. Schedule jobs. Deploy apps. All sandboxed.</h2>
178
179
  </div>
179
180
  <div class="tab-group">
180
181
  <div class="tab-bar">
@@ -197,16 +198,16 @@ mags login</code></pre>
197
198
  <table class="ref-table">
198
199
  <thead><tr><th>Command</th><th>Description</th></tr></thead>
199
200
  <tbody>
200
- <tr><td><code>mags run &lt;script&gt;</code></td><td>Execute a script in a fresh microVM</td></tr>
201
- <tr><td><code>mags ssh &lt;workspace&gt;</code></td><td>SSH into a VM (auto-starts if needed)</td></tr>
201
+ <tr><td><code>mags run &lt;script&gt;</code></td><td>Execute a script in a fresh sandbox</td></tr>
202
+ <tr><td><code>mags ssh &lt;workspace&gt;</code></td><td>SSH into a sandbox (auto-starts if needed)</td></tr>
202
203
  <tr><td><code>mags list</code></td><td>List recent jobs</td></tr>
203
204
  <tr><td><code>mags status &lt;id&gt;</code></td><td>Get job status</td></tr>
204
205
  <tr><td><code>mags logs &lt;id&gt;</code></td><td>Get job output</td></tr>
205
206
  <tr><td><code>mags stop &lt;id&gt;</code></td><td>Stop a running job</td></tr>
206
- <tr><td><code>mags sync &lt;workspace&gt;</code></td><td>Sync workspace to S3 (without stopping VM)</td></tr>
207
+ <tr><td><code>mags sync &lt;workspace&gt;</code></td><td>Sync workspace to the cloud now</td></tr>
207
208
  <tr><td><code>mags url &lt;id&gt; [port]</code></td><td>Enable public URL access</td></tr>
208
209
  <tr><td><code>mags workspace list</code></td><td>List persistent workspaces</td></tr>
209
- <tr><td><code>mags workspace delete &lt;id&gt;</code></td><td>Delete workspace + S3 data</td></tr>
210
+ <tr><td><code>mags workspace delete &lt;id&gt;</code></td><td>Delete workspace + cloud data</td></tr>
210
211
  <tr><td><code>mags cron add [opts] &lt;script&gt;</code></td><td>Create a scheduled cron job</td></tr>
211
212
  <tr><td><code>mags cron list</code></td><td>List cron jobs</td></tr>
212
213
  <tr><td><code>mags cron remove &lt;id&gt;</code></td><td>Delete a cron job</td></tr>
@@ -221,15 +222,16 @@ mags login</code></pre>
221
222
  <table class="ref-table">
222
223
  <thead><tr><th>Flag</th><th>Description</th></tr></thead>
223
224
  <tbody>
224
- <tr><td><code>-w, --workspace &lt;id&gt;</code></td><td>Persist files to S3 across runs</td></tr>
225
- <tr><td><code>--base &lt;workspace&gt;</code></td><td>Mount a workspace read-only as a base image</td></tr>
226
- <tr><td><code>-p, --persistent</code></td><td>Keep VM alive after script (sleeps when idle)</td></tr>
227
- <tr><td><code>-e, --ephemeral</code></td><td>No S3 sync &mdash; fastest execution</td></tr>
228
- <tr><td><code>-f, --file &lt;path&gt;</code></td><td>Upload file(s) to VM (repeatable)</td></tr>
225
+ <tr><td><code>-w, --workspace &lt;id&gt;</code></td><td>Keep files across runs (synced to the cloud)</td></tr>
226
+ <tr><td><code>--base &lt;workspace&gt;</code></td><td>Clone a workspace as a starting point (read-only)</td></tr>
227
+ <tr><td><code>-p, --persistent</code></td><td>Keep sandbox alive after script (sleeps when idle)</td></tr>
228
+ <tr><td><code>--no-sleep</code></td><td>Never auto-sleep this VM (requires <code>-p</code>)</td></tr>
229
+ <tr><td><code>-e, --ephemeral</code></td><td>No cloud sync &mdash; fastest execution</td></tr>
230
+ <tr><td><code>-f, --file &lt;path&gt;</code></td><td>Upload file(s) into the sandbox (repeatable)</td></tr>
229
231
  <tr><td><code>-n, --name &lt;name&gt;</code></td><td>Name the job for easy reference</td></tr>
230
232
  <tr><td><code>--url</code></td><td>Enable public HTTPS URL (requires <code>-p</code>)</td></tr>
231
233
  <tr><td><code>--port &lt;port&gt;</code></td><td>Port to expose for URL (default: 8080)</td></tr>
232
- <tr><td><code>--startup-command &lt;cmd&gt;</code></td><td>Command to run when VM wakes from sleep</td></tr>
234
+ <tr><td><code>--startup-command &lt;cmd&gt;</code></td><td>Command to run when sandbox wakes from sleep</td></tr>
233
235
  </tbody>
234
236
  </table>
235
237
  </div>
@@ -246,22 +248,25 @@ mags run -w myproject 'python3 app.py'
246
248
 
247
249
  # Base image &mdash; create a golden image, sync it, then reuse
248
250
  mags run -w golden -p 'apt install -y nodejs && npm install -g typescript'
249
- mags sync golden # persist to S3
251
+ mags sync golden # persist to cloud
250
252
  mags run --base golden 'npm test' # read-only, changes discarded
251
253
  mags run --base golden -w fork-1 'npm test' # fork: load golden, save to fork-1
252
254
 
253
- # SSH into a workspace (auto-starts VM if needed)
255
+ # SSH into a workspace (auto-starts sandbox if needed)
254
256
  mags ssh myproject
255
257
 
256
- # Persistent VM with public URL
258
+ # Persistent sandbox with public URL
257
259
  mags run -w webapp -p --url --port 8080 \
258
260
  --startup-command 'python3 -m http.server 8080' \
259
261
  'python3 -m http.server 8080'
260
262
 
263
+ # Always-on sandbox (never auto-sleeps)
264
+ mags run -w worker -p --no-sleep 'python3 worker.py'
265
+
261
266
  # Upload files and run
262
267
  mags run -f script.py -f data.csv 'python3 script.py'
263
268
 
264
- # Ephemeral (fastest &mdash; no S3 sync)
269
+ # Ephemeral (fastest &mdash; no cloud sync)
265
270
  mags run -e 'uname -a && df -h'
266
271
 
267
272
  # Cron job
@@ -292,7 +297,7 @@ export MAGS_API_TOKEN="your-token"</code></pre>
292
297
  <tr><td><code>enable_access(id, port)</code></td><td>Enable URL or SSH access</td></tr>
293
298
  <tr><td><code>upload_files(paths)</code></td><td>Upload files, returns file IDs</td></tr>
294
299
  <tr><td><code>list_workspaces()</code></td><td>List persistent workspaces</td></tr>
295
- <tr><td><code>delete_workspace(id)</code></td><td>Delete workspace + S3 data</td></tr>
300
+ <tr><td><code>delete_workspace(id)</code></td><td>Delete workspace + cloud data</td></tr>
296
301
  <tr><td><code>cron_create(**opts)</code></td><td>Create a cron job</td></tr>
297
302
  <tr><td><code>cron_list()</code></td><td>List cron jobs</td></tr>
298
303
  <tr><td><code>cron_delete(id)</code></td><td>Delete a cron job</td></tr>
@@ -308,12 +313,13 @@ export MAGS_API_TOKEN="your-token"</code></pre>
308
313
  <table class="ref-table">
309
314
  <thead><tr><th>Parameter</th><th>Description</th></tr></thead>
310
315
  <tbody>
311
- <tr><td><code>workspace_id</code></td><td>Persist files to S3 across runs</td></tr>
316
+ <tr><td><code>workspace_id</code></td><td>Keep files across runs (synced to the cloud)</td></tr>
312
317
  <tr><td><code>base_workspace_id</code></td><td>Mount a workspace read-only as base image</td></tr>
313
- <tr><td><code>persistent</code></td><td>Keep VM alive after script completes</td></tr>
314
- <tr><td><code>ephemeral</code></td><td>No S3 sync (fastest)</td></tr>
318
+ <tr><td><code>persistent</code></td><td>Keep sandbox alive after script completes</td></tr>
319
+ <tr><td><code>no_sleep</code></td><td>Never auto-sleep (requires <code>persistent=True</code>)</td></tr>
320
+ <tr><td><code>ephemeral</code></td><td>No cloud sync (fastest)</td></tr>
315
321
  <tr><td><code>file_ids</code></td><td>List of uploaded file IDs to include</td></tr>
316
- <tr><td><code>startup_command</code></td><td>Command to run when VM wakes</td></tr>
322
+ <tr><td><code>startup_command</code></td><td>Command to run when sandbox wakes</td></tr>
317
323
  </tbody>
318
324
  </table>
319
325
  </div>
@@ -347,6 +353,10 @@ job = m.run("python3 -m http.server 8080",
347
353
  startup_command="python3 -m http.server 8080")
348
354
  access = m.enable_access(job["request_id"], port=8080)
349
355
 
356
+ # Always-on sandbox (never auto-sleeps)
357
+ job = m.run("python3 worker.py",
358
+ workspace_id="worker", persistent=True, no_sleep=True)
359
+
350
360
  # Upload files
351
361
  file_ids = m.upload_files(["script.py", "data.csv"])
352
362
  m.run_and_wait("python3 /uploads/script.py", file_ids=file_ids)
@@ -398,12 +408,13 @@ export MAGS_API_TOKEN="your-token"</code></pre>
398
408
  <table class="ref-table">
399
409
  <thead><tr><th>Parameter</th><th>Description</th></tr></thead>
400
410
  <tbody>
401
- <tr><td><code>workspaceId</code></td><td>Persist files to S3 across runs</td></tr>
411
+ <tr><td><code>workspaceId</code></td><td>Keep files across runs (synced to the cloud)</td></tr>
402
412
  <tr><td><code>baseWorkspaceId</code></td><td>Mount a workspace read-only as base image</td></tr>
403
- <tr><td><code>persistent</code></td><td>Keep VM alive after script completes</td></tr>
404
- <tr><td><code>ephemeral</code></td><td>No S3 sync (fastest)</td></tr>
413
+ <tr><td><code>persistent</code></td><td>Keep sandbox alive after script completes</td></tr>
414
+ <tr><td><code>noSleep</code></td><td>Never auto-sleep (requires <code>persistent: true</code>)</td></tr>
415
+ <tr><td><code>ephemeral</code></td><td>No cloud sync (fastest)</td></tr>
405
416
  <tr><td><code>fileIds</code></td><td>Array of uploaded file IDs to include</td></tr>
406
- <tr><td><code>startupCommand</code></td><td>Command to run when VM wakes</td></tr>
417
+ <tr><td><code>startupCommand</code></td><td>Command to run when sandbox wakes</td></tr>
407
418
  </tbody>
408
419
  </table>
409
420
  </div>
@@ -439,6 +450,11 @@ const webJob = await mags.run('python3 -m http.server 8080', {
439
450
  const access = await mags.enableAccess(webJob.requestId, { port: 8080 });
440
451
  console.log(access.url);
441
452
 
453
+ // Always-on sandbox (never auto-sleeps)
454
+ await mags.run('python3 worker.py', {
455
+ workspaceId: 'worker', persistent: true, noSleep: true,
456
+ });
457
+
442
458
  // Upload files
443
459
  const fileId = await mags.uploadFile('script.py');
444
460
  await mags.runAndWait('python3 /uploads/script.py', { fileIds: [fileId] });
@@ -459,24 +475,26 @@ await mags.cronCreate({
459
475
  <section class="section" id="workspaces">
460
476
  <div class="container">
461
477
  <div class="section-title">
462
- <p>Workspaces</p>
463
- <h2>Persist what matters, reset the rest.</h2>
478
+ <p>Persistent Workspaces</p>
479
+ <h2>Your files survive. Every sandbox starts clean.</h2>
464
480
  </div>
465
481
  <div class="grid split">
466
482
  <article class="panel" data-reveal>
467
- <h3>What stays</h3>
483
+ <h3>Backed up to object storage</h3>
468
484
  <ul class="list">
469
- <li>Files and directories in your workspace</li>
470
- <li>Installed packages and dependencies</li>
471
- <li>Configuration and dotfiles</li>
485
+ <li>Files, packages, and configs persist automatically</li>
486
+ <li>Optional backup to S3-compatible object storage</li>
487
+ <li>Clone a workspace as a read-only base for new sandboxes</li>
488
+ <li>Survives reboots, sleep, and agent restarts</li>
472
489
  </ul>
473
490
  </article>
474
491
  <article class="panel" data-reveal>
475
- <h3>What resets</h3>
492
+ <h3>Fully isolated</h3>
476
493
  <ul class="list">
477
- <li>Running processes</li>
478
- <li>In-memory state</li>
479
- <li>Open ports</li>
494
+ <li>Every sandbox runs in its own isolated environment</li>
495
+ <li>No cross-user access &mdash; workspaces are private</li>
496
+ <li>Processes, memory, and ports reset between runs</li>
497
+ <li>Agents can't escape or affect the host</li>
480
498
  </ul>
481
499
  </article>
482
500
  </div>
@@ -488,7 +506,7 @@ await mags.cronCreate({
488
506
  <div class="container">
489
507
  <div class="section-title">
490
508
  <p>SDKs + API</p>
491
- <h2>Automate runs with Python, Node.js, or REST.</h2>
509
+ <h2>Let your agents spin up sandboxes programmatically.</h2>
492
510
  </div>
493
511
  <div class="tab-group">
494
512
  <div class="tab-bar">
@@ -508,7 +526,7 @@ m = Mags() # reads MAGS_API_TOKEN from env
508
526
 
509
527
  # Run and wait
510
528
  result = m.run_and_wait(
511
- "echo Hello from a VM!",
529
+ "echo Hello from a sandbox!",
512
530
  workspace_id="demo",
513
531
  )
514
532
  print(result["status"])
@@ -611,7 +629,7 @@ console.log(result.logs);</code></pre>
611
629
  <div class="container">
612
630
  <div class="section-title">
613
631
  <p>Resources</p>
614
- <h2>Extra pages for day-to-day work.</h2>
632
+ <h2>Everything you need to get started.</h2>
615
633
  </div>
616
634
  <div class="grid cards">
617
635
  <article class="card" data-reveal>
@@ -631,7 +649,7 @@ console.log(result.logs);</code></pre>
631
649
  </article>
632
650
  <article class="card" data-reveal>
633
651
  <h3>Claude skill</h3>
634
- <p>Install the Claude Code skill for microVM runs.</p>
652
+ <p>Install the Claude Code skill to run sandboxes from Claude.</p>
635
653
  <a class="text-link" href="claude-skill.html">Open Claude skill</a>
636
654
  </article>
637
655
  <article class="card" data-reveal>
@@ -649,9 +667,9 @@ console.log(result.logs);</code></pre>
649
667
  <div>
650
668
  <div class="brand">
651
669
  <span class="logo">Mags</span>
652
- <span class="tag">Instant sandboxes and runtime environments</span>
670
+ <span class="tag">Secure cloud sandboxes for the AI age</span>
653
671
  </div>
654
- <p>Build, test, and run from clean microVMs whenever you need them.</p>
672
+ <p>Secure, instant sandboxes for AI agents, developers, and automation.</p>
655
673
  </div>
656
674
  <div class="footer-links">
657
675
  <a href="login.html">Login</a>
@@ -667,7 +685,7 @@ console.log(result.logs);</code></pre>
667
685
  </div>
668
686
  </footer>
669
687
 
670
- <script src="script.js?v=3"></script>
688
+ <script src="script.js?v=5"></script>
671
689
  <script>
672
690
  (function() {
673
691
  var token = localStorage.getItem('microvm-access-token');