# How to run Claude Code in a cloud sandbox Install it with npm in a Linux microVM, store the API key as a secret, run `claude -p` on a cloned repo and copy the diff back. **On Runtime the agent runs on a machine of its own and never holds your key.** Every sandbox is a Firecracker microVM with Ubuntu 24.04 and Node.js 24, so Claude Code's npm package installs unchanged. Your Anthropic key is stored as a Runtime secret: the sandbox sees a worthless placeholder, and the host's proxy adds the real key only on requests to `api.anthropic.com`. A 2 vCPU, 4 GiB sandbox costs $0.03125 an hour while the agent waits on the model. Claude Code 2.1.282 was the current npm release on 25 September 2026. There are two ways to put the two together: | You want | Do this | | --------------------------------------------------- | ----------------------------------------------------------- | | Claude Code to work on a repo away from your laptop | Run Claude Code inside a sandbox (below) | | Claude Code on your machine to run code safely | Add Runtime's MCP server, and it creates sandboxes as tools | ## Store the key once Store your Anthropic key as a secret bound to Anthropic's API host. Every sandbox of your account then has `ANTHROPIC_API_KEY` set to a placeholder, and only an HTTPS request to that host carries the real value ([secrets sandboxes never see](/docs/security#secrets-sandboxes-never-see)). ```bash no-run printf %s "$ANTHROPIC_API_KEY" | npx withruntime secrets set ANTHROPIC_API_KEY --host api.anthropic.com ``` The value is read from standard input, so it never lands in your shell history. No API, tool or command returns it afterwards. A prompt injection that makes the agent print its environment prints the placeholder. ## Run Claude Code on a repo ```ts check import { writeFile } from "node:fs/promises"; import { Sandbox } from "withruntime"; const repo = "https://github.com/your-org/your-repo"; const task = "Find and fix the failing test in the parser, then run the tests."; await using sbx = await Sandbox.create({ diskMiB: 8192, timeoutSeconds: 3600 }); const slow = { check: true, timeoutMs: 600_000 } as const; await sbx.exec("npm install -g --prefix /workspace/.local @anthropic-ai/claude-code", slow); await sbx.exec(["git", "clone", "--depth", "1", repo, "/workspace/app"], slow); // From here on the agent reaches only the model and the npm registry. await sbx.network.set({ internet: true, allow: ["api.anthropic.com", "registry.npmjs.org"] }); const run = await sbx.exec( [ "claude", "--bare", "-p", task, "--allowedTools", "Bash,Read,Edit,Write", "--output-format", "json", ], { cwd: "/workspace/app", env: { CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC: "1" }, timeoutMs: 1_800_000, onStderr: (text) => process.stderr.write(text), }, ); const result = JSON.parse(run.stdout); console.log(result.result, result.total_cost_usd); await sbx.exec("git add -A && git diff --cached > /workspace/change.patch", { cwd: "/workspace/app", check: true, }); await writeFile("change.patch", await sbx.files.readText("/workspace/change.patch")); ``` ```python check import sys, json from withruntime import Sandbox repo = "https://github.com/your-org/your-repo" task = "Find and fix the failing test in the parser, then run the tests." with Sandbox.create(disk_mib=8192, timeout_seconds=3600) as sbx: sbx.exec("npm install -g --prefix /workspace/.local @anthropic-ai/claude-code", check=True, timeout_ms=600_000) sbx.exec(["git", "clone", "--depth", "1", repo, "/workspace/app"], check=True, timeout_ms=600_000) sbx.network.set(internet=True, allow=["api.anthropic.com", "registry.npmjs.org"]) run = sbx.exec( ["claude", "--bare", "-p", task, "--allowedTools", "Bash,Read,Edit,Write", "--output-format", "json"], cwd="/workspace/app", env={"CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC": "1"}, timeout_ms=1_800_000, on_stderr=sys.stderr.write, ) result = json.loads(run.stdout) print(result["result"], result["total_cost_usd"]) sbx.exec("git add -A && git diff --cached > /workspace/change.patch", cwd="/workspace/app", check=True) with open("change.patch", "w") as file: file.write(sbx.files.read_text("/workspace/change.patch")) ``` What each part does: - **`--prefix /workspace/.local`** installs the `claude` command into `/workspace/.local/bin`, which is first on the sandbox's `PATH`. Anthropic's guide warns against `sudo npm install -g`, and this needs no `sudo`. - **`--bare`** skips hooks, plugins, MCP servers and `CLAUDE.md` discovery, and reads `ANTHROPIC_API_KEY` from the environment. Anthropic recommends it for scripted runs. Pass `--append-system-prompt-file CLAUDE.md` to keep the repo's own instructions. - **`--allowedTools`** approves those tools without a prompt, since nobody is there to answer one. The sandbox is the boundary: the agent can run any command inside it and nothing outside it. - **The task is an array element,** so it reaches `claude` with no shell in between, whatever quotes or symbols it holds. - **`--output-format json`** returns the answer in `result`, with `session_id` and `total_cost_usd`, Anthropic's estimate of the model cost. - **The diff** comes back as a file, so a large change is never cut at the 64 KiB result limit. A timeout over 60 seconds streams the command, so the result keeps all of its output. `onStderr` shows progress as it happens. ## Headless flags that matter Checked in Anthropic's documentation on 25 September 2026: | Flag | What it does | | --------------------------------------- | ------------------------------------------------------------- | | `-p`, `--print` | Runs once, non-interactively, and exits 0 on success | | `--bare` | Skips local configuration; uses `ANTHROPIC_API_KEY` | | `--allowedTools "Bash,Read,Edit"` | Approves those tools without asking | | `--permission-mode acceptEdits` | Writes files without asking; other commands still need a rule | | `--output-format json` | One JSON result: `result`, `session_id`, `total_cost_usd` | | `--output-format stream-json --verbose` | One JSON event per line as the run goes | | `--continue`, `--resume ` | Carries on an earlier conversation | To run a second task on the same checkout, keep the sandbox and [pause it](/how-to/pause-and-resume-a-sandbox) between tasks: its files, memory and processes are kept, and compute billing stops. ## Give Claude Code Runtime as a tool The other direction: Claude Code on your own machine creates sandboxes, runs commands in them and reads files back, through Runtime's MCP server. ```bash no-run claude mcp add --scope user runtime -- npx -y withruntime mcp ``` The first call shows a link and a code. Approve **Connect agent** in your browser and every Runtime tool appears, with no key to copy and nothing to restart ([MCP](/docs/mcp#add-it-to-your-agent)). A machine already connected by `npx withruntime login` skips that step. To connect without the local bridge, add the remote server and run `/mcp` to sign in: ```bash no-run claude mcp add --transport http --scope user runtime https://api.withruntime.com/mcp ``` The tools Claude Code uses most: | Tool | What it does | | ----------------------------------------------------------- | --------------------------------------------------- | | `runtime_sandbox_create` | A new sandbox, ready when the call returns | | `runtime_sandbox_exec` | Runs a command and returns its exit code and output | | `runtime_sandbox_files_read`, `runtime_sandbox_files_write` | Reads and writes files in the sandbox | | `runtime_sandbox_network_set` | Narrows or turns off the sandbox's internet | | `runtime_sandbox_previews_create` | Shares a port at a private HTTPS address | | `runtime_secrets_set` | Stores a key the sandbox uses without seeing | In CI, `RUNTIME_API_KEY` from a secret manager replaces the browser approval. The full list is in [MCP tools](/docs/mcp#tools), and [coding agents](/docs/frameworks#coding-agents) has the same setup for Codex, Cursor and others. ## What it costs Runtime bills the CPU the agent uses at $0.025 per vCPU-hour, with a floor of a twentieth of a vCPU, and memory at $0.0075 per GiB-hour. A coding agent spends most of its time waiting on the model, which is the $0.03125 an hour rate for 2 vCPUs and 4 GiB; with both CPUs busy it is $0.08 an hour ([pricing](/docs/pricing)). Model tokens are billed by Anthropic on your key. New accounts get 50 free sandbox hours, no card: ```bash no-run npx withruntime sandbox run --trial -- node --version ``` The first run prints a link to approve in your browser. The same setup for OpenAI's agent is in [Codex in a sandbox](/integrations/codex), and [a sandbox for coding agents](/use-cases/coding-agent-sandbox) covers running many at once. ## Sources Checked 25 September 2026. - [Claude Code setup](https://code.claude.com/docs/en/setup): the npm package `@anthropic-ai/claude-code`, Node.js 22 or later, and the warning against `sudo npm install -g` - [Run Claude Code programmatically](https://code.claude.com/docs/en/headless): `-p`, `--bare`, `--allowedTools`, `--permission-mode`, `--output-format` - [Enterprise network configuration](https://code.claude.com/docs/en/network-config): `HTTPS_PROXY`, `NODE_EXTRA_CA_CERTS` and `CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC` - [@anthropic-ai/claude-code on npm](https://www.npmjs.com/package/@anthropic-ai/claude-code): version 2.1.282 Facts on this page were checked on 25 September 2026.