Skip to content

SDK

SDK operations cookbook

Current Python and TypeScript SDK calls, secure defaults, target helpers, and CLI fallbacks for common sandbox operations.

Use this page when you want a practical SDK operation and need to know whether to call the SDK today, use the CLI directly, or treat the helper as target API.

The shipped SDK runtime surface is intentionally smaller than the product target. Current examples use Sandbox.create(...), commands.start(...), the one-shot sandbox.exec(...), the full files.* API, TTLs, resources, network declarations, record mode, live mode, and cleanup. Logs, snapshots, and the lifecycle helpers are parity targets until the language SDK tests prove them.

Several of the CLI fallbacks below (machine proc, machine fs, machine pause, machine resume, machine checkpoint) are hidden advanced verbs: they work, but they do not appear in mvmctl machine --help.

OperationPython todayTypeScript todaySecure fallback today
Create sandbox recordingmvm.Sandbox.create(...)Sandbox.create(...)mvmctl build compile or mvmctl run --mode plan
Create live sandboxmvmctl run --mode live ./script.pymvmctl run --mode live ./script.tsmvmctl machine run
Start commandsandbox.commands.start([...])sandbox.commands.start([...])mvmctl machine proc start or mvmctl machine exec
Capture command resultsandbox.exec(*argv)sandbox.exec(argv)CLI command result and receipt paths
Write filesandbox.files.write(path, data)sandbox.files.write(path, data)mvmctl machine fs write
Read/list/remove filesandbox.files.read/list/remove(...)sandbox.files.read/list/remove(...)mvmctl machine fs read, mvmctl machine fs ls, mvmctl machine fs rm
LogsTarget helperTarget helpermvmctl machine logs
PortsNot claimedNot claimedDeclare ingress before boot: mvmctl machine run --port HOST:GUEST
Pause/resumeTarget helperTarget helpermvmctl machine pause, mvmctl machine resume
Checkpoint create/restoreTarget helperTarget helpermvmctl machine checkpoint create --class vm-full, mvmctl machine checkpoint restore
Stop cleanupcontext manager or kill()using/Symbol.dispose or kill()mvmctl machine stop
import mvm
with mvm.Sandbox.create(
"python-3.12",
workload_id="agent-tool",
ttl="30m",
include=["src"],
resources=mvm.resources(cpu_cores=1, memory_mb=512, rootfs_size_mb=1024),
network=mvm.network(mode="none"),
) as sandbox:
sandbox.files.write("/app/main.py", "print('hello from mvm')")
sandbox.commands.start(
["python", "/app/main.py"],
env={"MODE": "dev", "API_KEY": mvm.secret("api-key", type="bearer", hosts=["api.example.com"])},
)

Security notes:

  • the Python script itself runs on the host in record, plan, and live modes;
  • secret references are recorded as references, not copied as raw values;
  • commands.start(...) starts work and returns a handle; use sandbox.exec(...) when you want the exit code and captured output back;
  • the context manager records or performs cleanup through kill().

Run modes:

Terminal window
mvmctl build compile ./sandbox.py --out /tmp/sandbox-ir
mvmctl run --mode plan ./sandbox.py
mvmctl run --mode live ./sandbox.py

The shipped one-shot is sandbox.exec(...), live mode only. It returns an ExecResult carrying the exit code and the captured stdout/stderr:

result = sandbox.exec("python", "/app/main.py", timeout=30)
print(result.exit_code)
print(result.stdout)
print(result.stderr)

ExecResult carries no run or audit identifier yet. Use the CLI receipt path (mvmctl run --receipt ...) when automation needs audit correlation.

The file API is symmetric and shipped in both SDKs. Everything but write is live mode only; in record mode these raise a mode error rather than guessing:

sandbox.files.write("/work/input.json", b"{}")
data = sandbox.files.read("/work/output.json")
entries = sandbox.files.list("/work")
sandbox.files.remove("/work/output.json")

Treat bytes returned from the guest as untrusted and possibly sensitive.

Logs and ports should keep policy visible:

for event in sandbox.logs(follow=True, redact=True):
print(event.message)
# Ingress is declared in Sandbox.create(..., network={"ports": [...]})
# before the signed plan is admitted.

Until language helpers are shipped, declare ingress through machine run --port or the manifest. Bind host ports explicitly and avoid wildcard listeners unless the workflow requires them.

Lifecycle helpers should expose the same state model as the CLI:

snapshot = sandbox.snapshot(name="after-index")
sandbox.pause()
sandbox.resume(snapshot=snapshot.id)
sandbox.stop()
sandbox.destroy()

Until those helpers are shipped, use:

Terminal window
mvmctl machine pause agent-sandbox
mvmctl machine resume agent-sandbox
mvmctl machine checkpoint create agent-sandbox --class vm-full
mvmctl machine checkpoint restore CHECKPOINT_ID
mvmctl machine stop agent-sandbox

Snapshots and cold state can contain memory, files, process state, and credentials. Retention and deletion policy should be explicit in automation.