Skip to main content

sandboxa

sandboxa runs a command inside a restricted environment scoped to a target project directory.

It is designed to reduce accidental host exposure while still allowing practical project work.

What it does

  • Launches via systemd-run --user --pty.
  • Applies isolation properties:
    • ProtectHome=tmpfs
    • TemporaryFileSystem=$HOME:rw,mode=700,...
    • PrivateTmp=true
    • PrivateDevices=true
  • Sets the command working directory to the target project path.
  • Binds the target project path into the sandbox.
  • Optionally binds extra paths (--extra-data-path / YAML extra_data_paths).
  • Optionally binds OpenCode configuration paths when allow_features includes opencode.
  • Optionally forwards Wayland/X11 clipboard access when allow_features includes clipboard.
  • Applies InaccessiblePaths for YAML excluded_paths entries.
  • Refuses to run if a marker path exists in project (default: .profile).

Security model

  • Uses systemd-run --user isolation properties to reduce what the launched process can see from the host (ProtectHome=tmpfs, a writable tmpfs mounted at $HOME, PrivateTmp=true, PrivateDevices=true).
  • Grants filesystem access by explicit bind mounts only:
    • target project path
    • optional OpenCode config paths when allow_features includes opencode
    • optional extra_data_paths
  • Supports explicit deny-listing inside project scope via excluded_paths (InaccessiblePaths) for paths that currently exist.
  • allow_features: [clipboard] / --allow-feature clipboard exposes desktop-session IPC for clipboard integration. On Wayland this requires access to the compositor socket, which can allow more than clipboard-only interaction depending on the compositor.
  • Adds a safety guard against accidentally sandboxing a complete home-like directory by refusing to run when the marker path exists (default: .profile).
  • Applies strict config validation (pydantic, unknown YAML keys are rejected) to prevent silent misconfiguration.

Non-goals

  • Not a full container/VM boundary; this is a practical isolation wrapper, not a hardened multi-tenant sandbox.
  • Not a replacement for system-level mandatory access controls or seccomp policy authoring.
  • Not a network isolation tool; networking behavior is not managed here.
  • Not a privilege-escalation mechanism; it runs as the invoking user via systemd-run --user.
  • Not a generic policy engine; supported controls are intentionally narrow and centered on path exposure for local development workflows.

Requirements

  • Linux with user systemd session support (systemd-run --user).
  • Python 3.
  • Python packages:
    • ruamel.yaml
    • pydantic

Installation

Dependencies:

pip install pydantic ruamel.yaml

Install sandboxa from PyPI:

pipx install sandboxa

Install/upgrade from source:

pipx install git+ssh://gitlab@gitlab.silicann.systems:2224/silicann/infrastructure/sandboxa.git

Install/upgrade via cloning the repository:

git clone ssh://gitlab@gitlab.silicann.systems:2224/silicann/infrastructure/sandboxa.git
cd sandboxa
pipx install .

Usage

./sandboxa \
  [RUN_COMMAND] \
  [--project-path PATH] \
  [--extra-data-path PATH ...] \
  [--excluded-path PATH ...] \
  [--allow-feature NAME ...] \
  [--refuse-if-exists NAME] \
  [--config-file FILE] \
  [--no-reconnect] \
  [--dry-run] \
  [-- COMMAND_ARGS...]

Common examples:

# Run default command (opencode) in current directory
./sandboxa

# Run bash in current directory sandbox
./sandboxa bash

# Target explicit project directory
./sandboxa --project-path /path/to/project

# Pass args to run command
./sandboxa bash -- -lc "echo smoke-ok"

# Add extra bind paths
./sandboxa --extra-data-path /data/shared --extra-data-path /mnt/cache

# Override excluded paths from CLI
./sandboxa --excluded-path build/ --excluded-path secrets/

# Do not check for existing sessions to be resumed.
./sandboxa opencode --no-reconnect

# Allow Wayland/X11 clipboard tools such as wl-copy/wl-paste
./sandboxa --allow-feature clipboard

# Preview effective config and command without executing
./sandboxa bash --dry-run -- -lc "echo smoke-ok"

Configuration file

By default the script reads user config from ~/.config/sandboxa.yaml and project config from .sandboxa.yaml in the target project directory. Use --config-file to override the project config path; absolute paths are supported.

Supported keys:

  • allow_features: <list[string]> (see Feature Templates below)
  • extra_data_paths: <list[path]>
  • excluded_paths: <list[string]>
  • refuse_if_exists: <string>

Example:

allow_features:
  - opencode

extra_data_paths: []

excluded_paths:
  - build/
  - secrets/

refuse_if_exists: .profile

Precedence:

  • CLI arguments override YAML values, except --allow-feature adds to the configured/default feature set.
  • Project YAML values override user YAML values for most keys.
  • For allow_features and excluded_paths, user and project YAML values are merged.
  • YAML values override built-in defaults.

Feature Templates (allow_features)

Even in a constrained environment there is sometimes the need to use data from your real home directory. This could be the configuration of your favorite editor or the cache of your userspace package manager.

Some popular use-cases are implemented in sandboxa in order to ease the burden of finding the required files to be accessible in the sandbox.

The following contexts are supported.

Keyword for allow_features Purpose Limitations
clipboard Wayland/X11 clipboard integration exposes desktop-session IPC; disabled by default
opencode OpenCode -
podman Podman not working for root-less containers (see issue)
ssh OpenSSH agent and key material exposes ~/.ssh and optionally SSH_AUTH_SOCK if set
vim VIM without history (use extra-data_path: [~/.vim/] if you really need it)

License

This project is licensed under GNU GPL v3 or later. See LICENSE for the full text.

Metadata

Release files for sandboxa 0.3.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for sandboxa 0.3.0
File Size Uploaded Provenance
sandboxa-0.3.0.tar.gz 24.2 kB Without provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for sandboxa 0.3.0
File Interpreter ABI Platform
sandboxa-0.3.0-py3-none-any.whl Python 3 none any Details

Total release size: 45.0 kB

Release files / sandboxa-0.3.0.tar.gz

Download URL sandboxa-0.3.0.tar.gz
Size 24.2 kB
Tags Source
SHA-256 checksum
How to use checksums
7cc3bd96b362fdbc232fd13569adb0ed5b6092e3c012c29742220250361bae49
BLAKE2b-256 checksum
How to use checksums
82eb680d62b447d8093a905e91e7efacda1d7f37b69dd889d0ecc7e9a3b5f513
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via python-httpx/0.28.1

Release files / sandboxa-0.3.0-py3-none-any.whl

Download URL sandboxa-0.3.0-py3-none-any.whl
Size 20.7 kB
Tags Python 3
SHA-256 checksum
How to use checksums
564ebdcbd0d6c14d178ee0b837a8676c48c228ba679b786a6ca5da6b807947b2
BLAKE2b-256 checksum
How to use checksums
b71a8e66887ae9d62ca49044b1af6dcf106b3a498dd25f42e19693260ef33397
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via python-httpx/0.28.1

Security for sandboxa 0.3.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page