Skip to main content

Sandboxed AI agent workspace with MCP bridge

Project description

kennelbox

A local sandboxed AI agent workspace CLI. Agents like OpenClaw and Hermes Agent connect to a project directory via MCP (Model Context Protocol) — with hard restrictions on filesystem scope, command execution, and network access.

╔══════════════════════════════╗
║  ██╗  ██╗██████╗             ║
║  ██║ ██╔╝██╔══██╗            ║
║  █████╔╝ ██████╔╝            ║
║  ██╔═██╗ ██╔══██╗            ║
║  ██║  ██╗██████╔╝            ║
║  ╚═╝  ╚═╝╚═════╝             ║
╠══════════════════════════════╣
║  KENNELBOX  //  v0.1.0       ║
║  agent sandbox + MCP bridge  ║
╠══════════════════════════════╣
║  $ kennelbox run --agent <x> ║
╚══════════════════════════════╝

Features

  • CWD lock — agents can only read/write inside the directory where kennelbox init was run
  • Auto-venv — detects Python, Node, or generic projects and sets up an isolated environment
  • Firejail sandbox (required) — every tool call (commands and file I/O) runs inside firejail with filesystem whitelisting, network blocking, and seccomp filtering
  • Command allowlist — explicit per-project command rules; unknown = blocked. Inline code-execution flags (-c, -e, --eval, …) are blocked even for allowed interpreters
  • Resource caps — configurable limits on file read/write sizes and command output
  • MCP bridge — stdio JSON-RPC 2.0 server compatible with any MCP-capable agent

Requirements

  • Python 3.10+
  • Linux (Ubuntu / Zorin OS or compatible)
  • firejailrequired; kennelbox refuses to start without it

Install firejail

sudo apt install firejail

firejail provides the kernel-level isolation boundary. There is no software-only fallback — without firejail, kennelbox run exits with an error.


Installation

One-line installer (recommended)

git clone https://github.com/datacarismo/kennelbox.git
cd kennelbox
bash install.sh

The installer checks your Python version, installs firejail via apt (required), installs the package via pipx (preferred) or pip (fallback), and verifies kennelbox is on your PATH.

Options:
  --yes           accept all prompts non-interactively
  --no-firejail   skip the firejail apt step (kennelbox will not run until it's installed)

Manual install

git clone https://github.com/datacarismo/kennelbox.git
cd kennelbox
pipx install --editable .    # or: pip install -e .

pipx is recommended — it installs into an isolated venv and avoids PEP 668 "externally managed environment" errors on modern Debian/Ubuntu.

Via pip (once published)

pip install kennelbox

Quick Start

cd /path/to/your/project

# 1. Initialize the sandbox
kennelbox init

# 2. Check the rules
kennelbox rules

# 3. Start a sandboxed agent session (stdio MCP)
kennelbox run --agent openclaw

# 4. Check status
kennelbox status

# 5. Tear down when done
kennelbox release

CLI Reference

Command Description
kennelbox init Initialize .kennelbox/ in the current directory
kennelbox run --agent <name> Start sandboxed MCP session for the named agent
kennelbox rules Show allow/blocklist tables
kennelbox status Show sandbox state (agent, network, firejail)
kennelbox release Delete .kennelbox/ and tear down the sandbox

All commands accept --cwd <path> to target a different directory.


Configuration

On init, kennelbox creates a .kennelbox/ directory with two config files:

.kennelbox/allowlist.toml

Controls which commands and file extensions agents may access.

[commands]
allowed = ["ls", "cat", "grep", "python3", "pip", "node", "npm", "git status", "git log", "git diff"]
# Flags enabling inline code execution — blocked regardless of base command
blocked_args = ["-c", "-e", "--eval", "--exec", "-x", "--command"]
# Advisory only: matches are logged as warnings but NOT blocked
warn_patterns = ["rm -rf", "sudo", "curl", "wget", "nc", "chmod 777", "mkfs", "dd", "shutdown", "reboot"]

[limits]
max_read_bytes = 10485760    # 10 MB
max_write_bytes = 10485760   # 10 MB
max_output_bytes = 1048576   # 1 MB — command output truncated beyond this

[files]
allowed_extensions = [".py", ".js", ".ts", ".json", ".toml", ".yaml", ".md", ".txt"]

Unknown commands default to BLOCKED. Dotfiles and sensitive filenames (.env, .pem, .key, etc.) are always denied regardless of the extension allowlist.

.kennelbox/sandbox.toml

Firejail profile options.

[firejail]
network = false          # block outbound network
read_only_home = true    # no writes outside CWD
restrict_above_cwd = true
seccomp = true           # drop dangerous syscalls

MCP Bridge

kennelbox exposes a JSON-RPC 2.0 server (MCP-compatible) over two transports:

stdio (default) — the server starts on stdin/stdout and a local agent connects to it.

HTTP (--http) — for remote agents (e.g. an agent on a VPS reaching your machine over Tailscale):

kennelbox run --agent hermes --http --host 100.x.x.x --port 7333
  • A bearer token is required — auto-generated and printed if you don't pass --token
  • Binds 127.0.0.1 by default; pass --host (e.g. your Tailscale IP) to accept remote connections
  • Optional --allowed-ip (repeatable) restricts clients by source IP on top of the token
  • GET /health for liveness; POST / for JSON-RPC
  • Every HTTP request goes through the same allowlist + firejail pipeline as stdio

Available MCP Tools

Tool Description
read_file Read a file relative to the project root
write_file Write a file relative to the project root
edit_file Replace an exact, unique string in a file (fails on zero or multiple matches)
list_directory List directory contents
run_command Run an allowlisted shell command

All calls are validated against the allowlist before execution. Path traversal above the project root is always blocked.


Connecting OpenClaw

Configure OpenClaw to use kennelbox as its MCP server:

{
  "mcpServers": {
    "kennelbox": {
      "command": "kennelbox",
      "args": ["run", "--agent", "openclaw"],
      "transport": "stdio"
    }
  }
}

Connecting Hermes Agent

Add to your Hermes Agent config:

{
  "mcp": {
    "transport": "stdio",
    "command": "kennelbox run --agent hermes"
  }
}

Project Structure

kennelbox/
├── kennelbox.py          # CLI entrypoint (typer)
├── config/
│   ├── allowlist.toml    # default permitted commands (copied to .kennelbox/ on init)
│   └── sandbox.toml      # default firejail profile options
├── sandbox/
│   ├── jail.py           # firejail wrapper logic
│   └── venv_mgr.py       # auto-venv setup (Python / Node / generic)
├── agent_bridge/
│   └── server.py         # MCP stdio JSON-RPC 2.0 server
├── pyproject.toml
└── README.md

Security Model

The firejail sandbox is the security boundary. The allowlist is policy/UX guidance layered on top — it shapes what a well-behaved agent can request, but kernel-level isolation is what actually contains a misbehaving one. firejail is therefore required; kennelbox refuses to start without it.

  1. Filesystem — firejail whitelists only $CWD within the home tree. Credential directories (~/.ssh, ~/.gnupg, ~/.aws, ~/.config/gcloud, etc.) are explicitly blacklisted. /tmp and /dev are replaced with private views (--private-tmp, --private-dev).
  2. All tool I/O is sandboxed — not just run_command: read_file, write_file, and list_directory also execute inside firejail.
  3. Network — disabled by default (net=none). Set network = true in sandbox.toml to enable.

    Note: this applies to the firejail subprocesses. The kennelbox process itself and the agent connecting over stdio are outside the sandbox — LLM API calls (to Anthropic, OpenAI, etc.) are unaffected.

  4. Commands — only commands in allowed run. Argument flags enabling inline code execution (-c, -e, --eval, --exec, -x, --command) are rejected even for allowed interpreters. warn_patterns are advisory only — logged, never enforced.
  5. Files — extension allowlist plus unconditional denial of dotfiles and sensitive filenames (.env, .pem, .key, .cert, .pfx, .p12). Writes to .kennelbox/ (the config directory) are always blocked.
  6. Path escape — every path is resolved and containment-checked against the project root (Path.relative_to, not string prefix) before any I/O.
  7. Resource caps — file reads/writes and command output are size-limited (configurable in [limits]).
  8. Syscalls — firejail's default --seccomp filter (maintained upstream, more complete than any hand-rolled list).

kennelbox does not require root. firejail handles privilege separation at the kernel level via user namespaces.


License

MIT — see LICENSE

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

kennelbox-0.1.1.tar.gz (21.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

kennelbox-0.1.1-py3-none-any.whl (20.7 kB view details)

Uploaded Python 3

File details

Details for the file kennelbox-0.1.1.tar.gz.

File metadata

  • Download URL: kennelbox-0.1.1.tar.gz
  • Upload date:
  • Size: 21.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for kennelbox-0.1.1.tar.gz
Algorithm Hash digest
SHA256 1e6d5f344c6917aee4ddc0d1efa68617b56f6e44b41fe2ce39d39a2f0f65bd22
MD5 86fab5ee2988fa027fd27210fa82deb9
BLAKE2b-256 dbf40544cf6025c03788a8c76267d6abbcf6627ef9c6dce94e4dd9a7961311d9

See more details on using hashes here.

Provenance

The following attestation bundles were made for kennelbox-0.1.1.tar.gz:

Publisher: publish.yml on datacarismo/kennelbox

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file kennelbox-0.1.1-py3-none-any.whl.

File metadata

  • Download URL: kennelbox-0.1.1-py3-none-any.whl
  • Upload date:
  • Size: 20.7 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for kennelbox-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 425c8f33843495899c92506fdefacfe06ac74a696030ebb7f5310625b78a323f
MD5 776efcb8751596275892e51ef6a6b93d
BLAKE2b-256 139c8cb4f5d740ff91ab15144223925bf013aa04c6417a305ef397526604f116

See more details on using hashes here.

Provenance

The following attestation bundles were made for kennelbox-0.1.1-py3-none-any.whl:

Publisher: publish.yml on datacarismo/kennelbox

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page