Security wrapper for AI coding agents — credential isolation + OS sandbox.
make install # installs to ~/.local/bin
make install PREFIX=/usr/local # installs to /usr/local/binOn first run, ~/.config/jailrun/config.toml is auto-generated and the process exits, prompting you to review the config.
# launch an agent inside the sandbox
jailrun claude
jailrun codex exec "fix the bug"
jailrun gemini
jailrun kiro-cli
# specify AWS profile(s)
AGENT_AWS_PROFILES=staging jailrun claude
# token management
jailrun token add --name github:fine-grained-myorg
jailrun token rotate --name github:fine-grained-myorg
jailrun token list
# repository ruleset protection
jailrun ruleset # auto-detect from git remote
jailrun ruleset --dry-run # preview without applyingClaude Code, Codex, Gemini CLI, Kiro CLI
| Layer | Mechanism | Bypassable? |
|---|---|---|
| OS sandbox | Seatbelt (macOS) / systemd-run (Linux) | No (kernel-enforced) |
| Credential isolation | Temp credentials via env vars | No (set before exec) |
| Service-side limits | IAM Role / Fine-grained PAT | No (server-side) |
Config file: ~/.config/jailrun/config.toml
| Key | Type | Default | Description |
|---|---|---|---|
allowed_aws_profiles |
list | ["default"] |
Allowed AWS profiles |
default_aws_profile |
string | "default" |
Default AWS profile when none specified |
gh_token_name |
string | "classic" |
Short token name (expanded to jailrun:github:<name>) |
keychain_profile |
string | "allow" |
macOS Keychain access: "allow" / "deny" / "read-cache-only" |
sandbox_extra_deny_read |
list | [] |
Additional read-deny paths (23 paths blocked by default) |
sandbox_extra_allow_write |
list | [] |
Additional write-allow directories |
sandbox_extra_allow_write_files |
list | [] |
Additional write-allow files |
sandbox_passthrough_env |
list | [] |
Env vars to pass through to sandbox |
Some config keys can be overridden at runtime via environment variables:
| Env Var | Overrides | Example |
|---|---|---|
AGENT_AWS_PROFILES |
allowed_aws_profiles selection |
AGENT_AWS_PROFILES=staging jailrun claude |
AWS_PROFILE |
default_aws_profile |
AWS_PROFILE=dev jailrun claude |
GH_TOKEN_NAME |
gh_token_name |
GH_TOKEN_NAME=fine-grained jailrun claude |
SANDBOX_PASSTHROUGH_ENV |
sandbox_passthrough_env |
SANDBOX_PASSTHROUGH_ENV="KEY1 KEY2" jailrun claude |
AGENT_AWS_PROFILES → AWS_PROFILE → DEFAULT_AWS_PROFILE in config
(highest) (shell env) (fallback)
Uses systemd-run (no extra install if systemd is available). GitHub tokens are managed via secret-tool (GNOME Keyring):
sudo apt install libsecret-tools gnome-keyring # Ubuntu/Debian
jailrun token add --name github:classicThe AppArmor-primary sandbox path requires securityfs to be mounted at
/sys/kernel/security. WSL2 does not mount it automatically.
Mount it manually (one-time per session):
sudo mount -t securityfs securityfs /sys/kernel/securityTo persist across reboots, add an entry to /etc/fstab:
securityfs /sys/kernel/security securityfs defaults 0 0
Out of scope: jailrun does not provide a built-in helper for mounting
securityfs without root, nor an automatic mount at startup. If you want
this to be transparent, handle it in your dotfiles or systemd user units.
Under the AppArmor primary path on Linux/WSL2, credential candidate files
(e.g. .env, .aws/credentials) are denied for read, write/create/append,
lock and symlink operations (AppArmor mode flags r / w / k / l).
This blocks both reading existing credentials and creating or overwriting
them from inside the sandbox. Non-credential files (e.g. notes.txt) keep
working normally.
On WSL2, systemd's IPAddressDeny/IPAddressAllow properties are silently
ignored because cgroup BPF-based IP filtering does not work under the WSL2
systemd integration. The proxy starts and HTTPS_PROXY is set, but the
agent can bypass it by connecting directly.
To enforce network restriction on WSL2, use a network namespace so the agent can only reach the proxy:
# One-time setup (requires sudo, idempotent)
sudo scripts/wsl2-netns-setup.shThis is kernel-enforced and cannot be bypassed from inside the namespace.
When the agentns namespace exists, jailrun automatically detects it and:
- Binds the proxy to
10.200.0.1(ephemeral port) instead of127.0.0.1 - Launches the agent inside the namespace via
NetworkNamespacePath
So after running the setup script, a normal jailrun claude will use the
namespace automatically. No sudo is required at runtime.
Out of scope: jailrun does not manage the namespace lifecycle. Handle setup and teardown in your dotfiles or systemd units.
SSO session expired. Re-login:
aws sso login --profile <profile-name>Launch with AGENT_SANDBOX_DEBUG=1 to disable write restrictions (read denials remain active) and print the exec command to stderr:
AGENT_SANDBOX_DEBUG=1 jailrun claudeSandbox write restrictions may be the cause. Isolate by calling the binary directly:
/opt/homebrew/bin/claude # bypass the wrapperInside the agent, confirm the sandbox is active:
cat ~/.aws/config # should show "Operation not permitted"
For architecture, file structure, and advanced usage, see docs/README.md.
MIT