# Bondage > Bondage is a local C launcher for coding agents. It verifies exact paths and exact hashes, optionally releases secrets through envchain-xtra, optionally applies nono sandbox profiles, and keeps shell logic out of the trust boundary. ## Summary Bondage narrows the launch boundary around coding agents. The goal is not to prove that every dependency is good. The goal is to stop trusting shell aliases, mutable PATH resolution, and familiar shim names as if they were trustworthy launch identities. Bondage makes the actual launch explicit: exact absolute paths, exact hashes, optional secret release, optional sandbox policy, then exec. ## Why it exists - Coding agents should not run loose with live API keys and other secrets. - Familiar command names often hide weak dependency provenance and mutable package trees. - Broad ambient environment access is too generous by default. - Shell wrappers are useful for convenience but poor as a long-term security boundary. ## Philosophy - Use a small local launcher instead of growing more shell policy glue. - Prefer explicit trust in exact artifacts over ambient trust in names. - Let the operating system do the parts it is already better at doing. - Keep each layer narrow: - Bondage: launch verification and policy expansion - envchain-xtra: secret release - nono: sandbox enforcement ## Trust anchors - The operating system remains the strongest available layer for secret storage and signing identity. - Keychain is the preferred secret store when envchain-xtra is used. - Signing identity, where available, is useful as an approval and drift signal. - Bondage should trust exact artifacts, not a shell alias or mutable PATH result. - nono remains the enforcement layer for sandbox permissions when enabled. ## What it defends against - PATH drift and surprise binary replacement - Shell wrappers quietly becoming the policy engine - Mutable launch chains for JS-based agents - Accidental secret release to the wrong target - Confusion between sandboxed and rawdog paths ## What it does not solve - Blessing a bad npm tree in the first place - Host compromise before launch - A malicious tool you explicitly pinned and approved - Supply-chain review for dependencies you never audited - Human judgment failures about what should get secrets ## Preferred trust chain ```text shell name ↓ bondage ↓ [envchain-xtra] ↓ [nono] ↓ exact target ``` ## Installation ```sh brew tap nvk/tap brew install nvk/tap/agent-bondage brew install nvk/tap/envchain-xtra ``` ## Repositories - Homepage: https://agentbondage.org/ - Source: https://github.com/nvk/bondage - Getting Started: https://github.com/nvk/bondage/blob/main/GETTING_STARTED.md - Trust Model: https://github.com/nvk/bondage/blob/main/TRUST_MODEL.md - envchain-xtra: https://github.com/nvk/envchain-xtra - Homebrew tap: https://github.com/nvk/homebrew-tap ## Key facts - Maintainer: https://github.com/nvk - Language: C - Current launcher baseline: agent-bondage / bondage 0.2.7 - Current secret-release baseline: envchain-xtra 1.3.1 - Current sandbox baseline: nono 0.61.1 - Current Codex nono pack baseline: always-further/codex 0.0.12 - Current Claude nono pack baseline: always-further/claude 0.0.16 - Current OpenCode nono pack baseline: always-further/opencode 0.0.5 - Companion secret layer: envchain-xtra - Optional sandbox layer: nono - Formula: `agent-bondage` - Installed command: `bondage` ## Basic workflow ```sh mkdir -p ~/.config/bondage cp /path/to/bondage.conf.example ~/.config/bondage/bondage.conf bondage hash-file /absolute/path/to/tool bondage verify codex ~/.config/bondage/bondage.conf bondage chain codex ~/.config/bondage/bondage.conf -- --help bondage exec codex ~/.config/bondage/bondage.conf -- --help ``` ## Upgrade workflow Treat upgrades as launcher-policy changes. Use portable variables in docs, tickets, and transcripts so local usernames and project paths do not leak: ```sh export BONDAGE_CONF="${BONDAGE_CONF:-$HOME/.config/bondage/bondage.conf}" export NONO_PROFILE="${NONO_PROFILE:-codex}" brew upgrade nono brew cleanup nono bondage --config "$BONDAGE_CONF" repin-globals bondage --config "$BONDAGE_CONF" doctor nono pull always-further/codex@0.0.12 --force nono pull always-further/claude@0.0.16 --force nono pull always-further/opencode@0.0.5 --force nono pin always-further/codex nono pin always-further/claude nono pin always-further/opencode nono list --installed nono profile show "$NONO_PROFILE" >/dev/null bondage --config "$BONDAGE_CONF" verify codex bondage --config "$BONDAGE_CONF" chain codex -- --help ``` Sandbox checks should confirm expected policy shape without exposing local project paths: ```sh for path in \ "$HOME/.ssh" \ "$HOME/.npmrc" \ "$HOME/.aws" \ "$HOME/Library/Keychains" do nono why --profile "$NONO_PROFILE" --path "$path" --op read done nono why --profile "$NONO_PROFILE" --path "$HOME/.config/nono/profiles" --op write nono why --profile "$NONO_PROFILE" --path "$HOME/.config/nono/profile-drafts" --op write ``` Expected shape: credential paths are denied, active profile writes are denied, and profile-drafts is writable only for profiles that intentionally support draft-and-promote profile edits. ## Wrapper rule Shell wrappers should stay thin. A thin wrapper should do little more than call: ```sh bondage exec ~/.config/bondage/bondage.conf -- "$@" ``` ## Hook rule Hooks can be useful as deterministic guards, but anything they print to an agent-visible transcript becomes prompt surface. Sandbox denials should be fixed in managed nono profiles and launcher config, not by injecting recovery workflows into the model context. If a hook reports a denial, keep it factual and short. Do not tell the agent to offer choices, wait, stop, or create new profile policy from hook feedback.