Claude Code's own per-command sandboxing (~/.claude/settings.json's
"sandbox" block) is redundant on top of this container - which is already
a real, working sandbox on its own - and it couldn't even function here
anyway (bwrap can't create a namespace on this host; even CAP_SYS_ADMIN
only got it to a mount-propagation error, not further). Rather than
leaving it half-broken, disable it properly: settings.json is mounted
read-only specifically so a session can't tamper with it, so it can't be
patched from inside - bin/claude-sandbox now generates a sandbox-specific
copy (real settings.json with sandbox.enabled forced to false) on the
host and mounts that instead. bubblewrap/socat (added for this last
commit, never actually working) are removed - nothing needs them now.
Also fixes a real bug found in the same session: sandbox-context.sh told
agents to worktree via `git worktree add ../<branch>`, a sibling of the
mounted project directory. That path isn't backed by real host storage -
only the exact bind-mounted directory is - so a worktree created there
(observed landing under /home/node/<branch> in practice) silently
disappears, along with whatever work went into it, when the container
exits. Now instructs `.worktrees/<branch>` under the project root instead,
plus a .git/info/exclude entry so it doesn't clutter the user's real
checkout's git status.
Test suite extended to 25: sandbox.enabled=false generation, no
bubblewrap/socat, and no worktree instruction pointing outside the mounted
project. All pass.