Initial commit
This commit is contained in:
@@ -0,0 +1,58 @@
|
||||
# Host Dispatch to Container Agents
|
||||
|
||||
## Question
|
||||
|
||||
Can host Claude decide which claude-bottle container to spin up for a task, while guaranteeing the work executes in the container and not on the host?
|
||||
|
||||
## Claude Code Agent Mechanisms
|
||||
|
||||
Claude Code provides two mechanisms for defining reusable agent behavior:
|
||||
|
||||
**Skills** (`.claude/skills/<name>/SKILL.md`) run inline in the main conversation context. They're reusable workflows invoked via `/skill-name`, with optional tool pre-approval.
|
||||
|
||||
**Subagents** (`.claude/agents/<name>.md`) run in an isolated context window with a custom system prompt and a declared tool allowlist. They're invoked by natural language, `@agent-name`, or `claude --agent`. The `tools:` frontmatter is enforced — the subagent cannot call tools not in the list. (See [Claude Code subagents docs](https://code.claude.com/docs/en/sub-agents.md), "Choose the subagent scope" and "Write subagent files" sections.)
|
||||
|
||||
"Isolated context window" means only conversational isolation (fresh LLM state, summarized output). It is not process, filesystem, or network isolation. Subagents still run on the host with full user permissions.
|
||||
|
||||
## The Reliability Problem
|
||||
|
||||
The previous approach used an MCP server to bridge host Claude and claude-bottle containers. It failed because host Claude had both work-capable tools (Edit, Write, Bash) and MCP dispatch tools. Claude could choose to do the work itself rather than dispatch, with no enforcement mechanism to prevent it.
|
||||
|
||||
## Why Tool Restriction Solves It
|
||||
|
||||
Claude Code's subagent `tools:` allowlist is architecturally enforced — not a prompt-level suggestion. If the host subagent is defined with only container-dispatch tools and no Edit/Write/Bash, it is incapable of doing implementation work. Dispatch becomes the only available path.
|
||||
|
||||
## Reliable Dispatch Architecture
|
||||
|
||||
Three pieces in combination give a 100% guarantee:
|
||||
|
||||
1. **Restricted host subagent** — a `.claude/agents/claude-bottle-dispatch.md` with `tools:` limited to MCP container tools and git-read operations. No Edit, Write, or arbitrary Bash.
|
||||
|
||||
2. **MCP server** — exposes tools the restricted host can call:
|
||||
- `list_agents()` — available agents from the manifest (host Claude decides which to use)
|
||||
- `run_agent(agent_name, task)` — starts a container non-interactively, returns a job ID
|
||||
- `get_status(job_id)` — check running/done
|
||||
- `get_output(job_id)` — read results
|
||||
|
||||
3. **Non-interactive container run mode** — `cli.sh run <agent> "<task>"` passes the task to `claude --print` inside the container and captures output. Currently `cli.sh start` is interactive only; this mode does not yet exist.
|
||||
|
||||
## Proposal
|
||||
|
||||
Build host-dispatch-to-container in two deliverables:
|
||||
|
||||
**Deliverable 1: Non-interactive run mode for claude-bottle**
|
||||
|
||||
Extend `cli.sh` with a `run <agent> <task>` subcommand. Starts the container, writes the task prompt to a file inside it (same `docker cp` pattern used for `--append-system-prompt-file`), invokes `claude --print` with the prompt, streams stdout back to the host, and exits when Claude finishes. Results committed and pushed from inside the container as usual.
|
||||
|
||||
**Deliverable 2: MCP server wrapping claude-bottle**
|
||||
|
||||
A minimal MCP server (bash or node) exposing `list_agents`, `run_agent`, `get_status`, `get_output`. Registered in the host Claude Code settings so a restricted dispatch subagent can call it.
|
||||
|
||||
The combination enforces the container boundary at the tool layer, not the prompt layer — making it structurally impossible for host Claude to do implementation work itself.
|
||||
|
||||
**Critical:** the tool restriction only applies within the dispatch agent's context. A normal Claude session has its full toolset and may never invoke the dispatch agent regardless of its description. The dispatch agent must be the *entry point* for the session, not an optional subagent a full-tool host might call. Two ways to enforce this:
|
||||
|
||||
- Launch with `claude --agent claude-bottle-dispatch` — makes the dispatch agent the primary agent for the session.
|
||||
- Set `agent: claude-bottle-dispatch` in the project `.claude/settings.json` — same effect automatically for any `claude` invocation in that directory.
|
||||
|
||||
Without one of these, the guarantee does not hold.
|
||||
@@ -0,0 +1,76 @@
|
||||
# Landscape: containerized Claude Code agent tools
|
||||
|
||||
Research into whether claude-bottle is redundant with existing projects, and
|
||||
whether it's worth publishing.
|
||||
|
||||
## Summary
|
||||
|
||||
The "Claude Code in Docker" space is active but not saturated. claude-bottle
|
||||
occupies a distinct position: no surveyed project combines all five of its
|
||||
defining features. Publishing is likely worthwhile, with the main risk being
|
||||
claudebox expanding to absorb the same niche.
|
||||
|
||||
## Closest competitor: claudebox
|
||||
|
||||
[RchGrav/claudebox](https://github.com/RchGrav/claudebox) is the most
|
||||
feature-complete analog. It runs Claude Code in Docker with per-project
|
||||
isolated images, 15+ pre-configured dev-language profiles, and per-project
|
||||
network firewall allowlists. Actively maintained with multiple forks.
|
||||
|
||||
What it lacks: manifest-driven named agents, per-agent env resolution modes
|
||||
(prompt / host-forward / literal), skill directory injection, per-agent system
|
||||
prompts, SSH-agent forwarding without copying private keys, home+project
|
||||
manifest merge.
|
||||
|
||||
## Other surveyed projects
|
||||
|
||||
- **textcortex/claude-code-sandbox → spritz** — evolved toward
|
||||
Kubernetes-native multi-agent infra; not bash-first or local-Docker.
|
||||
Original sandbox repo is archived.
|
||||
- **trailofbits/claude-code-devcontainer** — devcontainer config for security
|
||||
audits; not a general agent launcher.
|
||||
- **Several small solo repos** (arezi/claude-sandbox, nkrefman/claude-sandbox,
|
||||
VishalJ99/claude-docker) — lightweight Docker wrappers with no multi-agent
|
||||
config layer.
|
||||
- **Docker's official sandbox templates** — launch-and-run Dockerfiles plus an
|
||||
npm-based runtime; not a manifest-driven fleet manager.
|
||||
|
||||
## Adjacent (different model)
|
||||
|
||||
- **dagger/container-use** (mid-2025) — exposes an MCP server so the *agent*
|
||||
spins up its own containers with Git worktrees. Inverted model vs. claude-bottle
|
||||
(agent controls container rather than being launched into one by a manifest).
|
||||
Still marked early-development.
|
||||
- **E2B, Northflank, Cloudflare Sandbox SDK** — cloud-hosted SaaS sandbox
|
||||
runtimes; fundamentally different architecture.
|
||||
|
||||
## What no found project does
|
||||
|
||||
None combine:
|
||||
1. Named-agent JSON manifest with per-agent env resolution (prompt / host-forward / literal)
|
||||
2. Claude Code skills directory injection
|
||||
3. Per-agent system prompts
|
||||
4. SSH-agent key forwarding without copying private keys into the container
|
||||
5. Home + project manifest merge
|
||||
|
||||
## Publishing verdict
|
||||
|
||||
Worth publishing. Differentiators that matter to the target audience (power
|
||||
users running parallel Claude Code sessions with distinct personas/tooling):
|
||||
|
||||
- The bash-first, low-dependency design — competitors are npm-based or
|
||||
Kubernetes-native.
|
||||
- Named agents with distinct skills and system prompts, not just language profiles.
|
||||
- SSH forwarding without key copying.
|
||||
|
||||
Main risk: claudebox adds manifest/agent config. The space is moving fast
|
||||
enough that publishing sooner is better if establishing prior art matters.
|
||||
|
||||
Discovery will be slow without active promotion; an Anthropic Discord post or
|
||||
HN "Show HN" would do most of the work.
|
||||
|
||||
## Caveats
|
||||
|
||||
- GitHub search cannot surface private or very new repos comprehensively.
|
||||
- Counts (stars, forks) were not confirmed for every project.
|
||||
- Research conducted 2026-05-07; the space moves fast.
|
||||
@@ -0,0 +1,231 @@
|
||||
# Local vs. Remote Agent Execution: Security & Privacy Tradeoffs
|
||||
|
||||
Research notes on when to run containerized Claude Code agents on a remote machine
|
||||
outside the local network versus inside it, focusing on security and privacy concerns.
|
||||
Relevant to a potential claude-bottle extension for remote agent execution.
|
||||
|
||||
---
|
||||
|
||||
## The core mental model
|
||||
|
||||
The topology decision isn't "local = safe, remote = dangerous." The real variables are:
|
||||
**what can the agent reach if compromised**, **what's on the host if the container
|
||||
escapes**, and **whether credentials are short-lived and scoped**.
|
||||
|
||||
---
|
||||
|
||||
## Threat landscape by topology
|
||||
|
||||
### Local (current claude-bottle model)
|
||||
|
||||
- Container escape → developer laptop → `~/.ssh`, `~/.aws`, browser cookies, Keychain, everything
|
||||
- Outbound: Docker containers have full internet access by default; no egress monitoring on most home networks
|
||||
- Lateral movement: compromised container can reach the LAN — NAS, other machines, internal services
|
||||
- Notable: CVE-2025-59536 (CVSS 8.7, Feb 2026) — a poisoned `.claude/settings.json` in a repo gives RCE when Claude Code opens it. `--dangerously-skip-permissions` removes the last gate.
|
||||
- Supply chain: MCP servers, skills, and npm packages pulled during agent execution. ~20% of ClawHub skills were found malicious in early 2026.
|
||||
|
||||
**What local topology protects:**
|
||||
- No inbound attack surface — nothing listening on a public port
|
||||
- Secrets stay physically on your hardware; no transit risk
|
||||
- Network egress bounded by the host router
|
||||
|
||||
### Remote machine
|
||||
|
||||
- New inbound attack surface (SSH/API port must be open; CISA notes exploitation of remote access vulns within 9–13 days of disclosure)
|
||||
- Secrets must travel from local to remote — each transit is a new exposure class
|
||||
- If the VM has a cloud IAM role attached → blast radius includes cloud APIs (S3, RDS, IAM, etc.)
|
||||
- Compromised remote host can read env vars injected into containers, intercept docker exec sessions, exfiltrate skills and prompts
|
||||
- **Worst case:** a remote VM connected back to the LAN via VPN is the worst of both worlds — internet-facing attack surface + full LAN access. This pattern should never be built.
|
||||
- Multiple agents sharing the same remote host creates cross-tenant bleed risk.
|
||||
|
||||
**What remote topology can offer:**
|
||||
- Better isolation from the developer laptop — a compromised container doesn't reach `~/.ssh` or local credentials unless explicitly forwarded
|
||||
- Ephemeral compute — a cloud VM torn down after each session leaves no persistent attack surface
|
||||
- Cloud-native network controls (Security Groups, VPC firewall, PrivateLink) can be more granular than home router rules
|
||||
- VPC flow logs + CloudTrail give an audit trail that a home network doesn't
|
||||
|
||||
---
|
||||
|
||||
## Data sensitivity — when "on-prem" matters
|
||||
|
||||
Data that should not leave the local network absent extraordinary controls:
|
||||
|
||||
| Data type | Why |
|
||||
|---|---|
|
||||
| Private SSH keys | If copied to remote, stored outside your control; lateral movement via key reuse |
|
||||
| Secrets forwarded into containers (API tokens, OAuth tokens) | In-transit exposure; remote machine persistence risk |
|
||||
| Source code under NDA or with unreleased IP | Contractual and competitive risk |
|
||||
| PHI (HIPAA) | Requires BAA with every system that touches it; standard cloud VMs don't qualify |
|
||||
| PII of EU residents (GDPR) | Cannot legally transit US infrastructure without SCCs |
|
||||
| Internal API credentials for LAN systems | Sending to a remote agent that can reach back via VPN creates a remote-controlled pivot |
|
||||
|
||||
Data that can go remote with proper controls:
|
||||
- Public open-source code
|
||||
- Non-sensitive project scaffolding
|
||||
- Prompts that don't contain embedded secrets
|
||||
- Derived outputs (build artifacts, test results) that don't contain source data
|
||||
|
||||
---
|
||||
|
||||
## Blast radius comparison
|
||||
|
||||
### Worst case: local container compromise
|
||||
|
||||
1. Container escape via kernel exploit → developer laptop
|
||||
2. From laptop: `~/.ssh/id_rsa`, `~/.aws/credentials`, browser session cookies, macOS Keychain, `~/.claude`
|
||||
3. Lateral movement to LAN — internal services, NAS, other dev machines
|
||||
4. Outbound: anything the home/office network allows
|
||||
|
||||
### Worst case: remote container compromise
|
||||
|
||||
1. Container escape → remote host
|
||||
2. From remote host: host environment credentials, any attached IAM role, secrets in the host filesystem
|
||||
3. If a VPN or SSH tunnel links remote machine to local network → full lateral movement back through that tunnel
|
||||
4. Cloud API access if the VM has IAM permissions → S3, RDS, EC2, Secrets Manager, etc.
|
||||
|
||||
**Remote blast radius is potentially larger than local if:**
|
||||
- The remote VM has cloud IAM permissions broader than the local laptop environment
|
||||
- The remote machine is connected back to the local network via VPN (creating a pivot)
|
||||
- Multiple agents share the same remote host
|
||||
|
||||
**Remote blast radius is smaller if:**
|
||||
- The remote VM is strictly isolated (no VPN back to LAN)
|
||||
- IAM role is locked to minimum necessary permissions
|
||||
- Remote host is ephemeral and torn down after each session
|
||||
|
||||
Key insight: once a container is compromised via prompt injection, the blast radius is dominated by what the agent *can reach*, not by where it physically runs. Studies have measured an 82.4% inter-agent compromise rate in multi-agent systems.
|
||||
|
||||
---
|
||||
|
||||
## Credentials and secrets
|
||||
|
||||
### Local topology (current claude-bottle)
|
||||
|
||||
- Secrets live in the host environment or are prompted from `/dev/tty`
|
||||
- Forwarded to containers via `-e NAME` (not `=value`), never on argv, never in env-files for secrets
|
||||
- On container teardown, secrets are gone from that process space
|
||||
- Risk: container escape to host reaches the host env where the parent process ran
|
||||
|
||||
### Remote topology
|
||||
|
||||
Secrets must travel from their source to the remote machine. Mechanisms in increasing security order:
|
||||
|
||||
1. **SSH env forwarding (`AcceptEnv`/`SendEnv`)** — secrets in plaintext in the SSH session; logged by some SSH daemon configurations
|
||||
2. **Encrypted orchestration channel** — secrets encrypted in transit, but remote machine must decrypt and expose them in memory
|
||||
3. **Vault/cloud secrets manager + dynamic credentials** — remote machine fetches its own short-lived secrets; local machine never sends secrets at all (best option)
|
||||
|
||||
An 8,640x reduction in abuse window comes from switching from 90-day keys to 15-minute tokens. Static long-lived tokens (`CLAUDE_CODE_OAUTH_TOKEN`, `GITLAB_TOKEN`) are the biggest risk in a remote topology.
|
||||
|
||||
**Proxy-inject pattern:** agent makes unauthenticated requests; a proxy outside the container injects credentials per-request. The container never sees the raw token. Anthropic's secure deployment docs recommend this pattern.
|
||||
|
||||
---
|
||||
|
||||
## Egress and exfiltration risk
|
||||
|
||||
### Local topology
|
||||
|
||||
- Monitoring: whatever the home/office router supports — usually minimal
|
||||
- Containment: `--network none` + a proxy socket provides the strongest containment; claude-bottle does not currently do this
|
||||
- DLP: essentially none unless specifically deployed on the LAN
|
||||
- Domain fronting risk: even allowlisted-domain proxies can be bypassed via domain fronting — an agent that can reach `api.anthropic.com` could relay data to an attacker-controlled backend through that domain
|
||||
- **claude-bottle today: containers have full outbound internet access. No egress restrictions.**
|
||||
|
||||
### Remote topology (cloud VM)
|
||||
|
||||
- VPC flow logs capture every connection attempt by IP/port — better than most home networks if configured
|
||||
- Security Groups can allowlist specific endpoints; a NAT gateway can be locked down
|
||||
- DLP tooling is more mature in cloud environments (AWS Macie, GCP DLP API, Cloudflare AI Gateway)
|
||||
- But only if configured. A raw cloud VM with default settings has worse egress monitoring than a corporate network.
|
||||
|
||||
Strongest exfiltration controls for either topology:
|
||||
1. `--network none` in Docker + a unix socket proxy that enforces domain allowlists
|
||||
2. TLS inspection at the proxy to defeat domain fronting
|
||||
3. Audit log all outbound traffic at the proxy
|
||||
|
||||
---
|
||||
|
||||
## Compliance
|
||||
|
||||
### HIPAA
|
||||
|
||||
- PHI must stay within HIPAA-covered infrastructure. Standard commercial cloud VMs require a signed BAA with the provider. AWS Bedrock, Azure OpenAI, and Google Cloud can be configured with BAA coverage; a generic EC2 cannot.
|
||||
- If the agent processes any PHI, the remote machine must be in a HIPAA-qualified environment.
|
||||
- "Minimum necessary" rule: an agent with broad filesystem access to a repo containing PHI violates this unless carefully scoped.
|
||||
|
||||
### GDPR
|
||||
|
||||
- EU personal data cannot legally be sent to US infrastructure without Standard Contractual Clauses or adequacy decisions.
|
||||
- Local execution (if the developer is EU-based) sidesteps this. Remote execution on a US cloud VM requires SCCs.
|
||||
|
||||
### SOC2
|
||||
|
||||
- No specific data residency mandate, but all infrastructure that touches in-scope data must implement the trust criteria. A remote VM needs audit logs, access controls, and continuous monitoring — more operational overhead than local execution.
|
||||
|
||||
---
|
||||
|
||||
## Decision heuristics
|
||||
|
||||
| Scenario | Recommendation |
|
||||
|---|---|
|
||||
| Solo developer, personal projects, no regulated data | Local is fine; add egress proxy for defense-in-depth |
|
||||
| Regulated data (HIPAA, GDPR, SOC2) | Local unless the remote environment is fully qualified |
|
||||
| Long-running automated tasks, no secrets in content | Remote VM acceptable with egress controls and ephemeral lifecycle |
|
||||
| Parallel agent fleet | Remote VM cluster with per-agent IAM roles, strict egress, centralized secret management |
|
||||
| Agent receives credentials that give network access to LAN | Keep local; never build a VPN-connected remote agent that can pivot back to the LAN |
|
||||
| Source code with embedded secrets (`.env`, API keys in config) | Local only, or sanitize before sending to remote |
|
||||
| Lack infrastructure maturity for proper remote config | Local — a poorly configured VM is strictly worse than a well-configured local container |
|
||||
|
||||
---
|
||||
|
||||
## Concrete recommendations if extending claude-bottle for remote
|
||||
|
||||
1. **Never build the VPN-pivot pattern.** A remote agent connected back to the LAN via VPN is the worst of both worlds. If a remote agent needs LAN resources, expose those through a narrow API, not a VPN.
|
||||
|
||||
2. **Add `--network none` + a proxy socket, even locally first.** The single highest-leverage change available right now. Bounds egress to allowlisted domains, prevents arbitrary exfiltration regardless of topology. Anthropic's secure deployment docs show exactly how to do this.
|
||||
|
||||
3. **Use dynamic, short-lived credentials for the remote context.** Replace static tokens with per-task dynamically issued credentials (Vault with approle auth, or cloud workload identity federation). This eliminates the "credential concentration on remote host" problem.
|
||||
|
||||
4. **Proxy-inject credentials; don't send them to the container.** The proxy runs on the remote host (not in the container); the credential lives only in the proxy process.
|
||||
|
||||
5. **Scope IAM/cloud permissions to the minimum.** No `*:*` policies. No admin roles on the VM.
|
||||
|
||||
6. **Make the remote VM ephemeral.** Spin it up for the session, tear it down when done. No persistent credentials or data between sessions.
|
||||
|
||||
7. **Enable VPC flow logs and forward them somewhere.** Going remote buys you egress monitoring you don't have locally — but only if configured.
|
||||
|
||||
8. **Validate hooks before execution.** `init-work` / `init-free-agent` copies a project into the container. That project may contain poisoned `.claude/settings.json` hooks (CVE-2025-59536 vector). `--dangerously-skip-permissions` removes the last gate; consider validating hooks before execution.
|
||||
|
||||
---
|
||||
|
||||
## Bottom line
|
||||
|
||||
For the current claude-bottle use case (developer feature implementation, no regulated data,
|
||||
single developer), local execution is the right default. The biggest unaddressed risk
|
||||
right now isn't topology — it's that containers have unrestricted outbound internet access.
|
||||
Adding `--network none` + a proxy socket would be higher-leverage than any topology change.
|
||||
|
||||
Remote execution becomes worth the complexity for parallelism at scale, long-running
|
||||
unattended tasks, or strict separation of agent compute from developer hardware — but
|
||||
only with egress controls, ephemeral lifecycle, and dynamic credential management in place.
|
||||
|
||||
---
|
||||
|
||||
## Sources
|
||||
|
||||
- Penligent AI — AI Agents Hacking in 2026: Defending the New Execution Boundary
|
||||
- Repello AI — The Agentic AI security threat landscape in 2026
|
||||
- arxiv 2601.17548 — Prompt Injection Attacks on Agentic Coding Assistants
|
||||
- Unit42 (Palo Alto) — Navigating Security Tradeoffs of AI Agents
|
||||
- Trend Micro — Unveiling AI Agent Vulnerabilities Part III: Data Exfiltration
|
||||
- Help Net Security — 29 million leaked secrets in 2025: AI agents credentials are out of control
|
||||
- GitGuardian — Short-Lived Credentials in Agentic Systems: A Practical Trade-off Guide
|
||||
- Aembit — Securing AI Agents Without Static Credentials
|
||||
- Anthropic Docs — Securely Deploying AI Agents
|
||||
- Anthropic Engineering — Claude Code Sandboxing
|
||||
- TrueFoundry — Claude Code Sandboxing: Network Isolation, File System Controls
|
||||
- TrueFoundry — LLM Deployment in Regulated Industries: HIPAA, SOC2 & GDPR Playbook
|
||||
- MindStudio — AI Agent Compliance: GDPR SOC 2 and Beyond
|
||||
- OX Security — The Mother of All AI Supply Chains: Critical MCP Vulnerability
|
||||
- The Hacker News — Anthropic MCP Design Vulnerability Enables RCE
|
||||
- Straiker — Agent Hijacking: How Prompt Injection Leads to Full AI System Compromise
|
||||
- Seraphic Security — Secure Remote Access Best Practices 2025
|
||||
Reference in New Issue
Block a user