diff --git a/_includes/sandbox-example.tsx b/_includes/sandbox-example.tsx index 4a88487ae..6f5dfb683 100644 --- a/_includes/sandbox-example.tsx +++ b/_includes/sandbox-example.tsx @@ -5,9 +5,9 @@ export default function Raw(data: Lume.Data) { <>
Deno Sandbox{" "} - provide a sandboxed environment for evaluating JavaScript code. This is - useful for evaluating code that is not trusted or for testing code that - is not safe to run in the main runtime. + provides a sandboxed Linux microVM. This is useful for evaluating code + that is not trusted or for testing code that is not safe to run in your + main runtime.
{data.children} diff --git a/examples/sandbox/access_output.md b/examples/sandbox/access_output.md index 6876c6258..9b5f608e0 100644 --- a/examples/sandbox/access_output.md +++ b/examples/sandbox/access_output.md @@ -5,7 +5,8 @@ url: /examples/sandbox_access_output/ layout: sandbox-example.tsx --- -You can access string and binary output from commands in a sandbox. +You can access string and binary output from commands in a sandbox. This example +shows how to capture command output in whichever form your workflow needs: ```ts import { Sandbox } from "@deno/sandbox"; @@ -22,3 +23,14 @@ console.log("Text length:", result.stdoutText!.length); import fs from "node:fs"; fs.writeFileSync("output.png", result.stdout!); ``` + +Piping stdout lets you retrieve both the raw binary buffer and a decoded text +view from the same command, so you can handle files that mix binary and textual +data without re-running the command. + +Once you have the binary result, you can pass it directly to APIs such as +`fs.writeFileSync` to persist artifacts generated inside the sandbox, making it +easy to move data between the sandbox and your host environment + +This is useful when sandbox commands produce files (images, archives, etc.) that +you need to consume programmatically rather than just printing to the console. diff --git a/examples/sandbox/command_cancellation.md b/examples/sandbox/command_cancellation.md index 65235ba97..956c6d282 100644 --- a/examples/sandbox/command_cancellation.md +++ b/examples/sandbox/command_cancellation.md @@ -5,7 +5,9 @@ url: /examples/sandbox_command_cancellation/ layout: sandbox-example.tsx --- -You can cancel commands in a sandbox using the `KillController` class. +Being able to cancel sandbox commands is key when tasks hang or you need to +enforce timeouts. You can cancel commands in a sandbox using the +`KillController` class. ```ts import { KillController, Sandbox } from "@deno/sandbox"; @@ -28,3 +30,13 @@ try { console.log("Command was cancelled:", error); } ``` + +`KillController` lets you attach a cancellation signal to any sandbox command, +so you can abort long-running processes if they exceed a limit or the user +cancels the operation. + +After triggering `controller.kill()`, the awaiting call rejects; you can +intercept that rejection to log, clean up, or retry as needed. + +This pattern keeps sandbox automation responsive and prevents orphaned processes +from consuming resources indefinitely. diff --git a/examples/sandbox/custom_error_classes.md b/examples/sandbox/custom_error_classes.md index ff369c38e..b12eb9680 100644 --- a/examples/sandbox/custom_error_classes.md +++ b/examples/sandbox/custom_error_classes.md @@ -7,6 +7,12 @@ layout: sandbox-example.tsx You can handle errors with custom error classes in a sandbox. +Catching `SandboxCommandError` lets you differentiate sandbox command failures +from other exceptions. When the error is the `SandboxCommandError` class, you +can read structured fields such as `error.code` or format `error.message` to +decide whether to retry, escalate, or map exit codes to your own domain-specific +errors: + ```ts import { Sandbox, SandboxCommandError } from "@deno/sandbox"; @@ -21,3 +27,6 @@ try { } } ``` + +This makes it easier to build higher-level automation that reacts intelligently +to known failure modes instead of treating every thrown error the same. diff --git a/examples/sandbox/environment_variables.md b/examples/sandbox/environment_variables.md index 590b7d367..d87c5d006 100644 --- a/examples/sandbox/environment_variables.md +++ b/examples/sandbox/environment_variables.md @@ -21,3 +21,10 @@ await sandbox.env.set("NODE_ENV", "production"); const apiKey = await sandbox.sh`echo $API_KEY`.text(); console.log("API_KEY:", apiKey.trim()); ``` + +Setting environment variables through `sandbox.env.set()` keeps configuration +and secrets inside the sandbox, so scripts run with the expected context without +hardcoding values in source files. That’s helpful when you need per-run +configuration (API keys, modes like NODE_ENV) or want to propagate credentials +to multiple commands securely. The variables stay scoped to the sandbox session +and are available to any command you execute there. diff --git a/examples/sandbox/error_handling.md b/examples/sandbox/error_handling.md index 492ac59b3..46524844e 100644 --- a/examples/sandbox/error_handling.md +++ b/examples/sandbox/error_handling.md @@ -5,8 +5,8 @@ url: /examples/sandbox_error_handling/ layout: sandbox-example.tsx --- -Commands in a sandbox throw by default on non-zero exit. You can use the -`noThrow()` method to handle errors manually. +Handling sandbox command failures explicitly gives you predictable recovery +paths: ```ts import { Sandbox } from "@deno/sandbox"; @@ -25,3 +25,13 @@ const result = await sandbox.sh`exit 1`.noThrow(); console.log("Exit code:", result.status.code); // → 1 console.log("Success:", result.status.success); // → false ``` + +Deno Sandbox commands throw on any non-zero exit, so wrapping them in try/catch +lets you surface clean error messages or trigger fallback logic instead of +crashing the entire workflow. + +When you want to inspect failures without throwing, `.noThrow()` returns the +full status object, so you can branch on `status.code` or `status.success`, log +diagnostics, or retry specific commands without losing context. This pattern is +essential for robust automation where commands might fail due to user input, +transient network issues, or missing dependencies. diff --git a/examples/sandbox/evaluating_javascript.md b/examples/sandbox/evaluating_javascript.md index 6bae5f55e..442239fed 100644 --- a/examples/sandbox/evaluating_javascript.md +++ b/examples/sandbox/evaluating_javascript.md @@ -19,3 +19,9 @@ const result = await sandbox.deno.eval(` `); console.log("result:", result); ``` + +Calling `sandbox.deno.eval()` lets you run arbitrary JavaScript snippets +directly inside the sandbox’s Deno runtime without writing files or shelling +out. This is useful when you want to prototype logic, run small computations, or +inspect the sandbox environment itself quickly. Use it for dynamic scripts or +exploratory debugging where creating a full module would be overkill. diff --git a/examples/sandbox/javascript_repl.md b/examples/sandbox/javascript_repl.md index 4a781d1ea..0b023d7e8 100644 --- a/examples/sandbox/javascript_repl.md +++ b/examples/sandbox/javascript_repl.md @@ -1,15 +1,16 @@ --- -title: "Intereactive JavaScript REPL" +title: "Interactive JavaScript REPL" description: "Learn how to provide an interactive Deno REPL in a sandbox." url: /examples/sandbox_javascript_repl/ layout: sandbox-example.tsx --- -The `sandbox.deno.repl()` method can be used to provide an interactive Deno REPL -in a sandbox. +A REPL (Read–Eval–Print Loop) is an interactive execution session where you type +code, the environment reads it, evaluates it, prints the result, and then keeps +the session alive so you can continue running more code while preserving state. -This example shows how to start a Deno REPL in a sandbox and execute code -interactively. +The `repl()` method can be used to provide an interactive JavaScript REPL in a +sandbox. ```ts import { Sandbox } from "@deno/sandbox"; diff --git a/examples/sandbox/memory.md b/examples/sandbox/memory.md index bf6281ddf..4fac94196 100644 --- a/examples/sandbox/memory.md +++ b/examples/sandbox/memory.md @@ -29,6 +29,16 @@ const memInfo = await sandbox.deno.eval<{ total: number }>( console.log("Total memory:", memInfo.total); ``` +Configuring memoryMb when creating the sandbox lets you tune resource usage per +workload. Lightweight tasks can run in smaller sandboxes to conserve resources, +while data-heavy scripts or compilations can request up to 4 GB to avoid +out-of-memory failures. + +Since you can programmatically inspect the sandbox’s memory via +`Deno.systemMemoryInfo()`, you can verify allocations or adapt behavior based on +the measured limits. This control helps match sandbox capacity to your needs, +keeping performance predictable while managing costs. + Memory limits (may change in the future): - Minimum: 768MB diff --git a/examples/sandbox/spawn_subprocess.md b/examples/sandbox/spawn_subprocess.md index b5aed396d..a0a330ed4 100644 --- a/examples/sandbox/spawn_subprocess.md +++ b/examples/sandbox/spawn_subprocess.md @@ -5,7 +5,9 @@ url: /examples/sandbox_spawn_subprocess/ layout: sandbox-example.tsx --- -You can spawn subprocesses in a sandbox and get buffered output as seen below. +You can spawn subprocesses in a sandbox and get buffered output. For example, to +print the current working directory as seen below. This is useful for running +shell commands and scripts. ```ts import { Sandbox } from "@deno/sandbox"; @@ -16,4 +18,5 @@ const text = await sandbox.sh`pwd`.text(); console.log("result:", text); // → "/home/sandbox\n" ``` -For long‑running processes or large output, stream the stdout/stderr. +For long‑running processes or large output, stream the stdout/stderr instead of +buffering it all in memory. diff --git a/examples/sandbox/ssh_access.md b/examples/sandbox/ssh_access.md index fa64811d0..e0c93a2a2 100644 --- a/examples/sandbox/ssh_access.md +++ b/examples/sandbox/ssh_access.md @@ -5,7 +5,9 @@ url: /examples/sandbox_ssh_access/ layout: sandbox-example.tsx --- -The `sandbox.exposeSsh()` method can be used to provide SSH access to a sandbox. +SSH access allows you to connect to a sandboxed environment securely over the +SSH protocol. The `sandbox.exposeSsh()` method can be used to provide SSH access +to a sandbox. ```ts import { Sandbox } from "@deno/sandbox"; diff --git a/examples/sandbox/stream_output.md b/examples/sandbox/stream_output.md index 5a777ac7f..ccf165ce5 100644 --- a/examples/sandbox/stream_output.md +++ b/examples/sandbox/stream_output.md @@ -5,12 +5,12 @@ url: /examples/sandbox_stream_output/ layout: sandbox-example.tsx --- -You can stream output to a local file in a sandbox. +You can stream output to a local file in a sandbox. This avoids buffering entire +large artifacts in memory. -`child.stdout` is a Web `ReadableStream`. - -In Node, convert a Node `fs.WriteStream` to a Web `WritableStream` to pipe -efficiently. +If you generate something sizable inside the sandbox (like `big.txt` below), you +can pipe it out chunk-by-chunk over a `ReadableStream`, converting Node’s +`fs.WriteStream` to a Web `WritableStream` for efficient transfer. ```ts import { Sandbox } from "@deno/sandbox"; @@ -33,3 +33,7 @@ await child.stdout.pipeTo(Writable.toWeb(file)); const status = await child.status; console.log("done:", status); ``` + +This pattern keeps memory usage flat, works well for logs or big binaries, and +lets you persist sandbox results on the host without temporary files or stdout +truncation. diff --git a/examples/sandbox/template_literals.md b/examples/sandbox/template_literals.md index b52b9347c..fdec7bd08 100644 --- a/examples/sandbox/template_literals.md +++ b/examples/sandbox/template_literals.md @@ -5,7 +5,11 @@ url: /examples/sandbox_template_literals/ layout: sandbox-example.tsx --- -You can use template literal commands with variable interpolation in a sandbox. +These conveniences help you script sandbox tasks quickly while keeping command +construction correct and secure. + +Using `sandbox.sh` template literals lets you run shell commands inside the +sandbox more safely and ergonomically: ```ts import { Sandbox } from "@deno/sandbox"; @@ -25,3 +29,13 @@ await sandbox.sh`rm ${files}`; const data = await sandbox.sh`echo '{"count": 42}'`.json<{ count: number }>(); console.log(data.count); // → 42 ``` + +Variables interpolated into the template literal are auto-escaped, so even +awkward values like file names with spaces can be passed without worrying about +quoting or injection. + +Arrays expand into multiple arguments automatically, making batch operations +(e.g., deleting several files) concise without manual join logic. You can also +chain helpers such as `.json()` to parse command output directly into typed data +structures, eliminating brittle string parsing and keeping results strongly +typed. diff --git a/examples/sandbox/timeout_control.md b/examples/sandbox/timeout_control.md index eeccb675b..90f7c6b92 100644 --- a/examples/sandbox/timeout_control.md +++ b/examples/sandbox/timeout_control.md @@ -5,7 +5,9 @@ url: /examples/sandbox_timeout_control/ layout: sandbox-example.tsx --- -You can control how long your sandbox stays alive using the timeout option: +You can control how long your sandbox stays alive using the timeout option. +Controlling timeout lets you decide whether sandboxes vanish immediately when +your script finishes or keep running for a set duration: ```ts import { Sandbox } from "@deno/sandbox"; @@ -37,5 +39,17 @@ await reconnected.kill(); // At this point, the sandbox is no longer reconnectable ``` +The default "session" mode is fine for short-lived automation—resource cleanup +happens as soon as the client disposes. + +Duration-based timeouts ("30s", "5m", etc.) let you close the client connection +while the sandbox keeps state alive, so you can reconnect later (e.g., to +inspect logs, rerun commands, or share the sandbox ID with another process) +before the timeout expires. + +You still control lifecycle explicitly with a call to `kill()` to end the +sandbox early if you no longer need it, useful if your job finishes sooner than +expected. + > Need other timeout modes? Contact > deploy@deno.com. diff --git a/examples/sandbox/upload_files.md b/examples/sandbox/upload_files.md index 1642f1eb9..9528d59fa 100644 --- a/examples/sandbox/upload_files.md +++ b/examples/sandbox/upload_files.md @@ -19,3 +19,9 @@ await sandbox.fs.upload("./README.md", "./readme-copy.md"); // Upload a local directory tree into the sandbox current directory await sandbox.fs.upload("./my-project", "."); ``` + +Uploading files or entire directories with `sandbox.fs.upload()` lets you bring +your local artifacts into the sandbox environment before running commands there. +This is useful when your workflow depends on existing source folders, +configuration files, or test data—once uploaded, the sandbox can compile, test, +or process them without remote Git access or manual copy/pasting. diff --git a/examples/sandbox/vscode_instance.md b/examples/sandbox/vscode_instance.md index 0d029dc3d..f69e4a3f1 100644 --- a/examples/sandbox/vscode_instance.md +++ b/examples/sandbox/vscode_instance.md @@ -5,11 +5,12 @@ url: /examples/sandbox_vscode_instance/ layout: sandbox-example.tsx --- -The `sandbox.exposeVscode()` method can be used to provide a VSCode instance in -a sandbox. - -This example shows how to start a VSCode instance in a sandbox and print the url -of the running instance which you can then open in your browser. +Running `sandbox.exposeVscode()` spins up a full VS Code instance inside an +isolated sandboxed environment and exposes its URL so you can open it in a +browser. This is handy when you need a lightweight, disposable editor for demos, +workshops, or remote debugging: you can provision VS Code on demand without +installing anything locally, safely experiment with code inside a contained +workspace, and tear it down automatically once you’re done. ```ts import { Sandbox } from "@deno/sandbox"; diff --git a/examples/sandbox/web_framework.md b/examples/sandbox/web_framework.md index c0dcc13c4..e56154a9e 100644 --- a/examples/sandbox/web_framework.md +++ b/examples/sandbox/web_framework.md @@ -6,10 +6,10 @@ layout: sandbox-example.tsx --- With Deno Sandbox you can create a `package.json`, install dependencies, run a -web framework (Express), and expose it publicly over HTTP. +web framework (such as Express), and expose it publicly over HTTP. -This example shows how to create a minimal Express app inside the sandbox, runs -it on port 3000, and exposes it publicly using `sandbox.exposeHttp()`. +This example shows how to create a minimal Express app inside the sandbox, run +it on port 3000, and expose it publicly using `sandbox.exposeHttp()`. ```ts import { Sandbox } from "@deno/sandbox"; diff --git a/services/_data.ts b/services/_data.ts index 165406da7..eec410fd6 100644 --- a/services/_data.ts +++ b/services/_data.ts @@ -8,7 +8,7 @@ export const SidebarNav = [ href: "/deploy/", }, { - title: "Sandbox", + title: "Deno Sandbox", href: "/sandbox/", }, {