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

# Security and isolation

> How Boat isolates sandboxes, who can reach a sandbox, which credentials it holds, network rules, URLs with tokens, team access, data retention, compliance and uptime. Each topic links to its detail page.

This page is the map of Boat security. Each section is short and links to the page that has the details.

| Question | Short answer | Details |
| - | - | - |
| Can one sandbox see another? | No. Each sandbox is its own virtual machine. | [Isolation](#isolation-between-sandboxes) |
| Who can open my sandbox? | You. Members of your organization, for sandboxes it pays for. People you share it with. | [Who can reach a sandbox](#who-can-reach-a-sandbox) |
| Which of my secrets are inside? | What your environment gives. None with **Safe for third parties**. | [Credentials](#boat-credentials-inside-a-sandbox) |
| Can it reach the internet? | Outbound yes. Inbound only SSH and the ports you publish. | [Network](#network) |
| Who can open a public URL? | Anyone with the full URL. | [URLs that carry a token](#urls-that-carry-a-token) |
| How long is my data kept? Can I erase it? | 14 days after a stop. Delete erases it. | [Data](#data) |
| SOC 2? Uptime? | SOC 2 in progress. 99.95% measured sandbox uptime. Platform status on [status.ascii.dev](https://status.ascii.dev). | [Compliance and uptime](/compliance) |

## Give sandboxes to end users

To give an end user a sandbox, do these three things:

1. Start the sandbox in an environment with **Safe for third parties** on, or with `boat new --no-env`. No secret of yours goes in.
2. Give the user an API key limited to that one sandbox, if they need the API.
3. Treat every URL with a token as a password.

```bash theme={null}
boat env new customers
boat env set customers --safe-for-third-parties true
boat new --environment customers --json
boat api-key create tenant-42 --preset full-sandbox --sandbox bx_123 --ttl 30d
```

## Isolation between sandboxes

* Each sandbox is its own virtual machine, with its own kernel, disk and IP address.
* Sandboxes share no disk and no processes. They reach each other only over the network.
* The `user` account has passwordless `sudo`. Anyone with a shell in a sandbox is root in that sandbox.
* So treat everything inside a sandbox as readable and changeable by its user. This includes files, environment variables and the browser profile.
* The security boundary is between sandboxes and between accounts. Inside a sandbox, use normal Linux tools (users, file permissions, firewall rules) as on any server.

### One sandbox per end user

Give each end user their own sandbox. Containers inside one sandbox share its kernel, so Boat does not isolate them from each other. Boat also does not clean a sandbox between your users.

* To start fast, save a [named snapshot](/snapshots/templates) and start each user's sandbox with `boat new --from <name>`.
* If you must reuse one sandbox for many users, assume each user looks for traces of the user before. Run each job as a new Linux user, delete its files after the job, and keep no keys in the sandbox.

## Who can reach a sandbox

| Who | What they can do | Details |
| - | - | - |
| You, the creator | Everything | |
| Members of your organization | See every sandbox the organization pays for. Use it if it holds no personal logins. | [Shared sandboxes](/organizations/shared-sandboxes) |
| People you share a sandbox with | What the share allows | [Shared sandboxes](/organizations/shared-sandboxes) |
| An API key | What its scopes allow. A key limited with `--sandbox` reaches one sandbox only. | [Scopes](/api-keys/scopes) |
| An SSH key you added | A shell as `user` | [SSH access](/ssh-access) |
| Anyone with a URL that carries a token | That one port or desktop | [URLs that carry a token](#urls-that-carry-a-token) |

Snapshots and personal environments stay private to the person who made them. Read [Teams and organizations](/organizations).

## Boat credentials inside a sandbox

| Credential | Where | What it can do | Safe for third parties / `--no-env` |
| - | - | - | - |
| `ASCII_TOKEN` | Environment variable, `~/.bashrc` | Host ports of its own sandbox. Nothing else. | Stays |
| In-sandbox API key | `~/.config/ascii/boat/config.json` | Read, stop, exec, files, SSH, desktop, host and snapshots, on its own sandbox only. Read [Scopes](/api-keys/scopes#in-sandbox-api-key). | Removed |
| Your environment variables and secret files | Environment, files you configured | Whatever the secret allows | Removed |
| GitHub token, `gh` login, git credentials | `~/.config/gh/hosts.yml`, `~/.git-credentials` | Your repositories | Removed |
| AI logins and keys | `~/.claude/`, `~/.codex/` and others | Your AI provider accounts | Removed, or replaced by [proxy placeholders](/ai-credentials#the-ai-credentials-proxy) |

`ASCII_TOKEN` lets the user publish any port of their sandbox on a public URL under that sandbox's subdomain. It cannot reach your account or other sandboxes.

For the full list of what a protected sandbox does not receive, read [Access and credentials](/environments/access#what-a-normal-sandbox-receives).

### Check a sandbox

```bash theme={null}
boat exec bx_123 'echo "[$STRIPE_KEY]"; ls ~/.config/ascii/boat/config.json ~/.git-credentials 2>&1'
```

A protected sandbox prints `[]` and `No such file or directory` for each file.

### Sandboxes made from your own snapshots

A snapshot of a normal sandbox can contain your secrets. Resume or fork it with `--no-env` before an end user gets it. Boat removes the owner secrets before the sandbox becomes reachable. Read [Protect an existing sandbox](/environments/access#protect-an-existing-sandbox).

## API keys for end users

| Need | Use |
| - | - |
| The user works in one sandbox | `--preset full-sandbox --sandbox <id>` |
| The user only reads | `--preset read-only --sandbox <id>` |
| Your backend creates sandboxes | `--preset ci`. Keep this key on your server. |

* A key limited with `--sandbox` cannot see or touch other sandboxes. It cannot list keys or read billing.
* `full-sandbox` cannot create, resume, fork or delete. Your backend does that.
* Use a short `--ttl`. Revoke the key when the user leaves.
* Never give an end user an `admin` key or a key with `account.admin`. These can create more keys.

Read [Scopes](/api-keys/scopes).

## Network

| Direction | Default | How to change it |
| - | - | - |
| Inbound | Refused, except SSH and the ports that Boat uses | `host <port>` for a public URL. `ufw allow` for a raw port. Read [Public URLs](/hosting#raw-tcp-or-udp-ports). |
| Outbound | Open to the internet | Firewall rules inside the sandbox. Read [Block outbound internet](/hosting/firewall#block-outbound-internet-for-untrusted-code). |

* Boat has no API setting for network rules.
* The user is root, so the user can remove rules that you add as root. To keep a rule, run the untrusted code as a separate account without `sudo`.
* Snapshots do not keep firewall rules. Apply them again after each resume and fork.

## URLs that carry a token

| URL | Who can open it | How long |
| - | - | - |
| Protected public URL (`?_token=`) | Anyone with the full URL. No Boat sign-in. | Until you replace the token. Read [Replace a leaked token](/hosting#replace-a-leaked-token). |
| Public URL with `--public` | Anyone | Until `host hide` |
| Desktop URL (Moonlight) | Anyone with the full URL | Open within 10 minutes. Read [Embed the desktop](/desktop-streaming/urls-and-security#how-long-a-desktop-url-works). |
| VNC desktop URL | Anyone with the full URL | Until the port becomes public |
| Signed file upload or download URL | Anyone with the URL | 15 minutes, up to 1 hour. Read [Large files](/ssh-access#large-files). |

Create these URLs on your server. Send each one only to the user who needs it. Do not log them.

## Data

| Topic | Short answer | Details |
| - | - | - |
| How long Boat keeps data | While a sandbox runs, and 14 days after it stops. Named snapshots until you delete them. | [Data retention](/data-retention#how-long-boat-keeps-data) |
| Erase a sandbox | `boat delete <id>`. You cannot undo it. | [Delete](/data-retention/delete) |
| Keep nothing after a stop | Zero data retention | [Zero data retention](/data-retention/zero-data-retention) |
| No snapshots or no logs at all | Snapshots off, monitoring off | [Snapshots and monitoring off](/data-retention/snapshots-and-monitoring-off) |
| Where data is stored | Machines in Germany, Finland and France. Snapshot copies can be stored outside the EU. | [Compliance and uptime](/compliance#data-location) |
| AI keys | Keep real keys out of sandboxes with the AI credentials proxy | [AI credentials](/ai-credentials) |

SOC 2, uptime, data location and security reports are on [Compliance and uptime](/compliance).


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