Skip to main content
A sandbox has a simple lifecycle: create it, use it, stop it when it is idle, start it again when you need it, and remove it when you are finished. Stopping preserves the sandbox’s configuration and filesystem, while removing deletes its sandbox-owned state.

Create a sandbox

Locally, an attached SDK handle stops its sandbox when the client process exits. Cloud sandboxes are service-owned, so stop or remove them explicitly.
Creating a sandbox starts the microVM and waits until it is ready to accept commands. Give each sandbox a name so you can find and manage it later. Names must be non-empty and no longer than 128 UTF-8 bytes.
An attached local SDK handle normally stops its sandbox when the client process exits. See Keep a sandbox running when the sandbox should outlive that process.

Stop and start again

Stopping gracefully terminates guest processes and shuts down the VM. The sandbox moves to Stopped, but its configuration and filesystem remain available for the next start. The timeout behavior depends on the backend:
  • Local: stop() waits up to 10 seconds, then force-kills the sandbox if it is still running.
  • Cloud: stop() waits up to 6 minutes because shutdown may include creating a durable disk checkpoint. If the deadline expires, the SDK returns its typed stop-timeout error and stops waiting. It does not cancel or force-kill the accepted server-side stop, which may still complete afterward.
Use the explicit timeout option in your SDK to change how long the caller waits. On Cloud this remains an observation deadline, not a cancellation deadline. Use request_stop and wait_until_stopped separately when you want to submit the stop and manage observation yourself.
Use restart when you want to stop and start the sandbox in one operation. If it is already stopped or crashed, restart starts it directly. SDK receiver methods preserve the sandbox’s identity and configuration while replacing only the running VM instance.
CLI
On microsandbox cloud, timeout expiry cannot escalate to a force kill. Force controls are local-only, and detached-start controls affect only local process ownership.

Reuse or create a named sandbox

Use connect_or_create when your application wants a sandbox with a stable name but does not know whether it already exists. This is useful for workers, development environments, and services that reconnect after the client process restarts. The operation:
  • Connects if the sandbox is running
  • Starts it if it is stopped or crashed
  • Creates it if the name does not exist
Creation options are used only when a new sandbox is created. If worker already exists, its saved image, resources, environment, mounts, and other configuration are kept. To apply new configuration, use the local replacement workflow. On microsandbox cloud, where replacement is unavailable, remove the existing sandbox and then create it again.
If you already have a SandboxHandle, use connect_or_start to connect to that exact sandbox or start it when needed.

Keep a sandbox running

Detach a local sandbox when it should keep running after the client process exits. You can reconnect to it later by name.
You can also detach an existing SDK receiver with detach() (Detach in Go).

List and inspect

List sandboxes to discover what exists, or get one by name when you already know which sandbox you need.

Wait for a state

Use wait_until_stopped when another part of your application is responsible for stopping the sandbox and you only need to wait for it to finish.
Use wait_for_status (waitForStatus in TypeScript and WaitForStatus in Go) when you need to wait for a specific lifecycle state. It has no built-in timeout, so use the language’s normal timeout or cancellation primitive around it.

Change configuration

Use msb modify, or the SDK modify() methods, to change an existing sandbox without recreating it. Some changes apply immediately, some affect future commands, and some take effect after a restart.
See Live Modify for the change model, CPU and memory resize, labels, environment variables, secrets, and storage sizing.

Check health and keep a sandbox active

Ping and touch are currently available only for local sandboxes.
Use ping to check that a running sandbox’s guest agent is reachable. A ping is only a health check and does not reset the idle timer. Use touch when you intentionally want to keep the sandbox active.

Drain before stopping

Draining is currently available only for local sandboxes. Use a graceful stop on microsandbox cloud.
Use a drain when existing commands should finish but new commands should be rejected. The sandbox moves to Draining, waits for in-flight commands, and then stops. This is useful when rotating worker sandboxes without interrupting active jobs.

Stop an unresponsive sandbox

Force kill is currently available only for local sandboxes. Use a graceful stop on microsandbox cloud.
If a sandbox does not respond to a graceful stop, force-kill it. This ends the VM immediately without waiting for guest processes to shut down.

Destroy or remove

Use destroy when you have an SDK receiver and want to stop and remove that exact sandbox in one operation. It requests a graceful stop by default, escalates after the configured timeout, and refuses to act on a replacement that reused the name.
Use remove when the sandbox is already stopped and you want to delete it by name.
For a local sandbox, removal deletes sandbox-owned state while leaving independently managed resources intact: Removing a sandbox does not undo writes made to a named volume, bind mount, or user-supplied disk image. On cloud, removal deletes the remote sandbox resource; the local disk details above do not apply.

Automatic lifecycle policies

For production workloads, configure a maximum lifetime or idle timeout so sandboxes shut down automatically.

Lifecycle states

Most applications only need to distinguish between Running and Stopped. The complete set is useful for status displays and recovery logic. Some backends can also report Paused. Resume is not currently exposed through the SDKs, so start and connect operations do not treat a paused sandbox as stopped.

Names, handles, and concurrent callers

A sandbox name finds the current sandbox saved under that name. A Sandbox or SandboxHandle also carries an opaque stable ID (ID() in Go) for one exact saved sandbox. Treat the ID as an opaque value and use it for logging, correlation, and equality checks. If worker is removed and a different sandbox is later created with the same name, an old receiver will not act on the replacement. Lifecycle methods return SandboxReplaced or the language’s typed equivalent when they can detect this situation; an ID-addressed cloud request may instead report that the old resource no longer exists. Concurrent callers are safe to use with the named lifecycle APIs. create remains strict, so only one same-name creation succeeds. connect_or_create may reuse the sandbox created by another caller, and connect_or_start remains attached to the exact identity held by its handle. Calls that encounter Starting wait for the sandbox to become ready instead of launching a second runtime.

Logs and diagnostics

Use msb logs or the SDK logs() method to read captured output from running, stopped, or crashed sandboxes. For source semantics, boot errors, and diagnostic flows, see Logs.

Reference

For exact lifecycle APIs, see TypeScript, Rust, Python, or Go. For lifecycle commands and the REST surface, see Sandbox commands and the Cloud API.