> ## Documentation Index
> Fetch the complete documentation index at: https://docs-stg.outerlayer.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Build in a managed sandbox

> Run a runner on a Linux machine or a Mac with no Docker and no KVM, and build each item in a sandbox that OuterLayer provides.

A managed sandbox is a machine that OuterLayer starts for one build. The runner
stays on your machine. It needs no Docker, no KVM and no sandbox provider
account. It is the shortest way to a working runner on Linux or on a Mac.

OuterLayer turns managed sandboxes on for an organization. Ask OuterLayer to do
this before you set up the runner.

## What stays on your machine

* **The runner,** its config file and its host key.
* **The agent's credential and the repository tokens.** They never enter the
  sandbox.
* **The agent's session.** The runner keeps it and continues it on the next
  job of the work item.

The sandbox has no direct network access. A build reaches the network through
the runner's tunnel, so `runner.build.allowHosts` still applies.

## Set up the runner

Run this command on a Linux machine, in WSL2 or on a Mac:

```bash theme={"system"}
outerlayer runner init --sandbox
```

The command does not look at Docker or KVM. A machine that could run microVM
builds gets the same setup: the flag decides, not the machine.

It writes this block into the config file:

```json theme={"system"}
{
  "runner": {
    "hooks": { "provision": "builtin:sandbox", "cleanup": "builtin:sandbox" },
    "sandbox": { "provider": "outerlayer", "machine": "small", "docker": true }
  }
}
```

Add `--machine large` for a larger sandbox. Small is 2 vCPU and 8 GiB of
memory. Large is 4 vCPU and 16 GiB.

The rest of `runner init` is as it is for any runner. It asks for the runner
key and the agent's credential, and it sets up the service. The machine still
needs the agent's credential and 5 GB of free disk. A Linux machine or WSL2 also needs systemd. See
[Set up your first host](https://docs-stg.outerlayer.ai/set-up-a-host.md).

After it writes the block, the command asks the gateway whether it provides
sandboxes to this runner. It prints one line with the answer:

* **The gateway provides sandboxes.** Nothing more to do.
* **The gateway refuses for a reason that can pass.** Managed sandboxes are off
  for the organization. The line gives the reason. The
  block stays, and the exit code is 0.
* **The check could not be made.** The line says why. The block stays, and the
  exit code is 0.
* **The gateway provides no sandboxes.** A self-hosted gateway with no sandbox
  provider settings answers this way. The command leaves no `runner` block,
  sets up no service and exits with a code other than 0.

Run [`outerlayer runner check`](https://docs-stg.outerlayer.ai/reference/cli-runner#outerlayer-runner-check)
at any time to ask again.

## What it costs

The build's time in the sandbox counts as managed build-hours, at the size of
the sandbox. See
[Builds in a managed sandbox](https://docs-stg.outerlayer.ai/billing-and-trials.md#builds-in-a-managed-sandbox).

## On a Mac

A Mac can host this runner with no Docker and no Linux VM. Run the same
command:

```bash theme={"system"}
outerlayer runner init --sandbox
```

The command asks no question about a Linux VM. It writes the same block, and
it keeps the runner running as a launch agent. The launch agent is the file
`~/Library/LaunchAgents/ai.outerlayer.sandbox-runner.<unit name>.plist`. The
default unit name is `outerlayer-runner`. The agent runs as you, and the
command needs no `sudo`.

launchd starts the agent at login. It starts the runner again after a failure
and after an update. A runner that you stopped with `outerlayer runner stop`
stays stopped.

The runner reads the agent's credential from `claude.env` beside the config
file. The launch agent's file holds no credential.

Check the agent with `outerlayer runner status`. It prints a
`launch agent` line that says `loaded` or `not loaded`. To remove the agent,
run `outerlayer runner uninstall --service`.

If launchd refuses to load the agent, as it does over SSH with no session at
the screen, the command says so and exits 0. It leaves the block and the file in
place. Run `outerlayer runner install --service` from a session at the Mac's
screen to load the agent.

> [!WARNING]
>
> A build fails when the Mac sleeps. A sleeping Mac stops the runner, so the
> runner stops renewing the build's claim, and the claim runs out. Set a Mac that
> hosts a runner to stay awake. OuterLayer does not do this for you.

The agent runs only while you are logged in. Set the Mac to log in at start.

## Where it works

`--sandbox` works on Linux, WSL2 and macOS. It is refused on native Windows:
run the command in WSL2 there. It is also refused with `--vm`, and with a
config file that has a `runnerVm` block. Name another file with `--config` in
that case.

## Limits

* **The sandbox ends with the build.** The runner keeps no disk for the next
  job on the work item, so each job clones and sets up again.
* **No schedule runs.** A runner on managed sandboxes takes no run of a
  [schedule automation](https://docs-stg.outerlayer.ai/schedule-automations.md), because a run has no work item.
* **Restart the runner** after you add or remove `runner.sandbox.provider`. A
  runner that is running keeps the provider it started with.
* **When OuterLayer makes no sandbox for a build,** the build is not failed.
  The runner gives the item back, takes no work for 5 minutes, and then tries
  again.

The keys of the `runner.sandbox` block are in the
[config file reference](https://docs-stg.outerlayer.ai/reference/config-file.md#sandboxes-that-outerlayer-provides).
To build in a sandbox from a provider account of your own, see
[A sandbox provider account of your own](https://docs-stg.outerlayer.ai/reference/config-file.md#a-sandbox-provider-account-of-your-own).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.