Sandbox options
Configure sandbox behavior by passing options when creating a sandbox instance with getSandbox().
import { getSandbox } from '@cloudflare/sandbox';
const sandbox = getSandbox(binding, sandboxId, options?: SandboxOptions);Type: boolean
Default: false
Keep the container alive indefinitely by preventing automatic shutdown. When true, the container automatically sends heartbeat pings every 30 seconds to prevent eviction and will never auto-timeout.
How it works: The sandbox automatically schedules lightweight ping requests to the container every 30 seconds. This prevents the container from being evicted due to inactivity while minimizing resource overhead. You can also enable/disable keepAlive dynamically using setKeepAlive().
The keepAlive flag persists across Durable Object hibernation and wakeup cycles. Once enabled, you do not need to re-set it after the sandbox wakes from hibernation.
// For long-running processes that need the container to stay aliveconst sandbox = getSandbox(env.Sandbox, "user-123", { keepAlive: true,});
// Run your long-running processawait sandbox.startProcess("python long_running_script.py");
// Important: Must explicitly destroy when donetry { // Your work here} finally { await sandbox.destroy(); // Required to prevent containers running indefinitely}// For long-running processes that need the container to stay aliveconst sandbox = getSandbox(env.Sandbox, 'user-123', { keepAlive: true});
// Run your long-running processawait sandbox.startProcess('python long_running_script.py');
// Important: Must explicitly destroy when donetry { // Your work here} finally { await sandbox.destroy(); // Required to prevent containers running indefinitely}Type: string | number
Default: "10m" (10 minutes)
Duration of inactivity before the sandbox automatically sleeps. Accepts duration strings ("30s", "5m", "1h") or numbers (seconds).
// Sleep after 30 seconds of inactivityconst sandbox = getSandbox(env.Sandbox, "user-123", { sleepAfter: "30s",});
// Sleep after 5 minutes (using number)const sandbox2 = getSandbox(env.Sandbox, "user-456", { sleepAfter: 300, // 300 seconds = 5 minutes});// Sleep after 30 seconds of inactivityconst sandbox = getSandbox(env.Sandbox, 'user-123', { sleepAfter: '30s'});
// Sleep after 5 minutes (using number)const sandbox2 = getSandbox(env.Sandbox, 'user-456', { sleepAfter: 300 // 300 seconds = 5 minutes});Type: object
Configure timeouts for container startup operations.
// Extended startup with custom Dockerfile work// (installing packages, starting services before SDK)const sandbox = getSandbox(env.Sandbox, "data-processor", { containerTimeouts: { portReadyTimeoutMS: 180_000, // 3 minutes for startup work },});
// Wait longer during traffic spikesconst sandbox2 = getSandbox(env.Sandbox, "user-env", { containerTimeouts: { instanceGetTimeoutMS: 60_000, // 1 minute for provisioning },});// Extended startup with custom Dockerfile work// (installing packages, starting services before SDK)const sandbox = getSandbox(env.Sandbox, 'data-processor', { containerTimeouts: { portReadyTimeoutMS: 180_000 // 3 minutes for startup work }});
// Wait longer during traffic spikesconst sandbox2 = getSandbox(env.Sandbox, 'user-env', { containerTimeouts: { instanceGetTimeoutMS: 60_000 // 1 minute for provisioning }});Available timeout options:
instanceGetTimeoutMS- How long to wait for Cloudflare to provision a new container instance. Increase during traffic spikes when many containers provision simultaneously. Default:30000(30 seconds)portReadyTimeoutMS- How long to wait for the sandbox API to become ready. Increase if you extend the base Dockerfile with custom startup work (installing packages, starting services). Default:90000(90 seconds)
Environment variable overrides:
SANDBOX_INSTANCE_TIMEOUT_MS- OverrideinstanceGetTimeoutMSSANDBOX_PORT_TIMEOUT_MS- OverrideportReadyTimeoutMS
Precedence: options > env vars > SDK defaults
Type: Environment variables
Control SDK logging for debugging and monitoring. Set these in your Worker's wrangler.jsonc file.
Available options:
SANDBOX_LOG_LEVEL- Minimum log level:debug,info,warn,error. Default:infoSANDBOX_LOG_FORMAT- Output format:json,pretty. Default:json
{ "vars": { "SANDBOX_LOG_LEVEL": "debug", "SANDBOX_LOG_FORMAT": "pretty" }}[vars]SANDBOX_LOG_LEVEL = "debug"SANDBOX_LOG_FORMAT = "pretty"Use debug + pretty for local development. Use info or warn + json for production (structured logging).
Type: boolean
Default: false (will become true in a future version)
Lowercase sandbox IDs when creating sandboxes. When true, the ID you provide is lowercased before creating the Durable Object (e.g., "MyProject-123" → "myproject-123").
Why this matters: Preview URLs extract the sandbox ID from the hostname, which is always lowercase due to DNS case-insensitivity. Without normalization, a sandbox created with "MyProject-123" becomes unreachable via preview URL because the URL routing looks for "myproject-123" (different Durable Object).
// Without normalization (default)const sandbox1 = getSandbox(env.Sandbox, "MyProject-123");// Creates Durable Object with ID: "MyProject-123"// Preview URL: 8000-myproject-123.example.com// Problem: URL routes to "myproject-123" (different DO)
// With normalizationconst sandbox2 = getSandbox(env.Sandbox, "MyProject-123", { normalizeId: true,});// Creates Durable Object with ID: "myproject-123"// Preview URL: 8000-myproject-123.example.com// Works: URL routes to "myproject-123" (same DO)// Without normalization (default)const sandbox1 = getSandbox(env.Sandbox, 'MyProject-123');// Creates Durable Object with ID: "MyProject-123"// Preview URL: 8000-myproject-123.example.com// Problem: URL routes to "myproject-123" (different DO)
// With normalizationconst sandbox2 = getSandbox(env.Sandbox, 'MyProject-123', { normalizeId: true});// Creates Durable Object with ID: "myproject-123"// Preview URL: 8000-myproject-123.example.com// Works: URL routes to "myproject-123" (same DO)Use normalizeId: true when:
- Using preview URLs - Required for port exposure if your IDs contain uppercase letters
- New projects - Either enable this option OR use lowercase IDs from the start (both work)
- Migrating existing code - Create new sandboxes with this enabled; old uppercase sandboxes will eventually be destroyed (explicitly or after timeout)
Best practice: Use lowercase IDs from the start ('my-project-123' instead of 'MyProject-123').
Use custom sleepAfter values to:
- Reduce costs - Shorter timeouts (e.g.,
"1m") for infrequent workloads - Extend availability - Longer timeouts (e.g.,
"30m") for interactive workflows - Balance performance - Fine-tune based on your application's usage patterns
The default 10-minute timeout works well for most applications. Adjust based on your needs.
Use keepAlive: true for:
- Long-running builds - CI/CD pipelines that may have idle periods between steps
- Batch processing - Jobs that process data in waves with gaps between batches
- Monitoring tasks - Processes that periodically check external services
- Interactive sessions - User-driven workflows where the container should remain available
With keepAlive, containers send automatic heartbeat pings every 30 seconds to prevent eviction and never sleep automatically. Use for scenarios where you control the lifecycle explicitly.
- Expose services guide - Using
normalizeIdwith preview URLs - Preview URLs concept - Understanding DNS case-insensitivity
- Background processes guide - Using
keepAlivewith long-running processes - Lifecycle API - Create and manage sandboxes with
setKeepAlive() - Sandboxes concept - Understanding sandbox lifecycle