A secure, Docker-based sandbox for web development and CLI tooling. This template configures a Docker firewall container, isolating the main dev container. Also supports mounting project folders and files from external sources via SSHFS.
The firewall setup was an adaptation of Anthropic's original version. I split the firewall setup into a separate container. This allows firewall changes on the fly and avoids giving the main dev container NET_ADMIN / NET_RAW privileges.
- Isolated, non-root development container
- Firewall container to restrict outbound network traffic to approved domains
- Commands for updating firewall whitelist
- Configurable script for mounting project files with SSHFS
- Persistent history and configuration via Docker volumes
- Set up for Claude out of the box, but adaptable for any CLI/web development tool
web-dev-sandbox/
├── docker/
│ ├── firewall/
│ │ ├── Dockerfile_firewall # Firewall container image
│ │ ├── firewall-apply.sh # Firewall whitelist update helper script
│ │ ├── firewall-init.sh # Firewall init helper script
│ │ ├── fw # Whitelist commands (ls, add, remove, update)
│ │ └── whitelist.txt # Whitelisted domains
│ ├── .env # Project environment for container names
│ ├── docker-compose.yml # Combined firewall + main container
│ ├── docker.sh # Start main container and optionally rebuild
│ └── Dockerfile # Main container image
├── workspace/
│ ├── .claude/
│ │ └── settings.local.json # Claude project settings
│ ├── content
│ └── .claudeignore # Claude ignore
├── setup/
│ ├── mount.sh # Verify and remount SSHFS folders if necessary
│ └── start.sh # Reset mounts and containers, attach to sandbox
└── README.md # This file
Set the project name inside docker/.env. Defaults to my-project.
./docker/docker.sh [--build]
From fresh, this will completely build, start, and initialize the firewall and main container.
For subsequent runs, it will restart the main container (after starting the firewall if it wasn't already running).
If --build is supplied, it will rebuild, start, and reinitialize both containers again.
Manage the firewall whitelist with the ./fw script inside docker/firewall. It updates the firewall container's ipset atomically.
./fw ls Prints whitelist.txt
./fw add <domain> Adds a domain to whitelist.txt and updates the firewall.
./fw remove <domain> Removes a domain from whitelist.txt and updates the firewall.
./fw update Updates the firewall based on the current whitelist.txt.
By using SSHFS to mount folders, you can choose exactly what Claude (or whatever tool you choose) has access to.
Modify the CONTENT_PATH variable in mount.sh to point to your remote file server for each folder.
Run the script to initialize or refresh the mounts:
./setup/mount.sh
./setup/attach.sh
Your workspace will be mounted at /workspace. Dotfiles (e.g., .claudeignore) will be visible.
This is a quick way to reset the sandbox mounts, restart the main container, and attach all at once.
./setup/start.sh
Claude configuration is persisted:
claude_config → /home/node/.claude
Can be configured in the ./docker/docker-compose.yml file.
Swap the CLI/tool installation in Dockerfile (e.g., replace @anthropic-ai/claude-code). Your firewall and container isolation remain intact. Workspace and config volumes can be reused for any project.
- Firewall container handles network restrictions
- Root privileges are never exposed in main container
- Mounts are explicit; host system is protected