io.github.aniongithub/devcontainer-mcp is an MCP server that manages development container environments for AI coding agents. It supports creating, managing, and working inside dev containers across three backends: local Docker, DevPod, and GitHub Codespaces.
๐ ๏ธ Key Features
Dev container environment management via MCP
Backend support for local Docker
Backend support for DevPod
Backend support for GitHub Codespaces
๐ Use Cases
Let an AI agent operate within a dedicated dev container
Provision and manage isolated environments using dev containers
โก Developer Benefits
Integrates dev container workflows with an MCP server interface
Uses common dev container backends: Docker, DevPod, and Codespaces
โ ๏ธ Limitations
Limited to the dev container backends explicitly listed: local Docker, DevPod, and GitHub Codespaces
Give your AI agent its own dev environment โ not yours.
devcontainer-mcp is an MCP server that lets AI coding agents create, manage, and work inside dev containers across three backends: local Docker, DevPod, and GitHub Codespaces. The agent builds, tests, and ships code in an isolated container โ your laptop stays clean.
devcontainer-mcp local Docker demo
Works with GitHub Copilot, Claude, Cursor, opencode, and any MCP-compatible client.
The Problem
When AI agents write code, they need to run it somewhere. Today that means your host machine:
๐ด "Works on my machine" โ agents assume your local toolchain matches production
๐ด No isolation โ one project's dependencies break another
๐ด Security risk โ agents run arbitrary commands with your user privileges
๐ด Hardware constraints โ you're limited to your local machine's resources
The Solution
The devcontainer spec already defines reproducible, container-based dev environments. Every major project ships a .devcontainer/devcontainer.json. But AI agents can't use them โ until now.
devcontainer-mcp exposes 45 MCP tools that let any AI agent:
Spin up a dev container from any repo โ locally, on a cloud VM, or in Codespaces
Run commands inside the container โ builds, tests, linting, anything
Manage the lifecycle โ stop, restart, delete when done
Authenticate against cloud providers โ GitHub, AWS, Azure, GCP โ without ever seeing a raw token
code
Agent: "Let me build this project..."
โ auth_status("github") โ picks account
โ codespaces_create(auth: "github-you", repo: "your/repo")
โ codespaces_ssh(auth: "github-you", codespace: "...", command: "cargo build")
โ โ Built in the cloud. Your laptop did nothing.
How it works: The binary runs inside WSL; MCP clients on Windows launch it via wsl ~/.local/bin/devcontainer-mcp serve. The stdio transport works transparently across the WSL boundary. WSL 2 is required โ install it with wsl --install if you haven't already.
Backend CLIs (devpod, devcontainer, gh) are detected at runtime โ if one is missing, the MCP server returns a helpful error with install instructions.
Binaries available for linux-x64, linux-arm64, darwin-x64, and darwin-arm64.
Host Protection & Opt-Out
The installer configures two agent hooks (Claude Code & GitHub Copilot CLI) that activate only in a directory containing .devcontainer/devcontainer.json:
devcontainer-guard (PreToolUse) โ blocks shell/command execution on the host so the agent routes builds, tests, and runs through the MCP tools instead. Host-safe commands (git, gh) are allowlisted, and both hooks fail open โ if jq is missing or a payload can't be parsed, commands are allowed rather than blocked.
devcontainer-skill-loader (SessionStart) โ injects the SKILL.md usage guide as context.
Turning it off for a repo
Sometimes a project ships a stale or unmaintained .devcontainer that you don't actually want to route work through. To disable both hooks for that repo, drop a marker file at the repo root:
bash
touch .devcontainer-mcp-disable
When .devcontainer-mcp-disable is present, the guard allows host commands through and the skill-loader skips context injection โ the agent works locally as if no devcontainer were declared. Commit it (or add it to .gitignore for a local-only opt-out).
One-off bypass: to run a single host command without disabling the guard, include USER_CONFIRMED_HOST_OPERATION=1 anywhere in the command.
Architecture
graph TD
A[AI Agent / MCP Client] -->|stdio JSON-RPC| B[devcontainer-mcp]
subgraph "devcontainer-mcp"
B --> C[33 MCP Tools]
C --> D[Auth Broker]
C --> E[devcontainer-mcp-core]
end
D -->|opaque handles| C
E -->|subprocess| F[DevPod CLI]
E -->|subprocess| G[devcontainer CLI]
E -->|subprocess| H[gh CLI]
E -->|bollard API| I[Docker Engine]
F --> J[Docker / K8s / Cloud VMs]
G --> K[Local Docker]
H --> L[GitHub Codespaces]
Codespaces tools require an auth handle (e.g. "github-aniongithub"). The MCP server resolves it to the real token on each call via the CLI's native keyring.
Codespaces: GitHub CLI โ auth is handled by the auth_login tool
Self-Healing
When devcontainer_up, devpod_up, or codespaces_create fails, the full build output (including errors) is returned to the agent. The agent can read the error, fix the Dockerfile or devcontainer.json, and retry โ making the dev environment a dynamic, agent-managed asset rather than a static prerequisite.
Multi-container workspaces
The devcontainer spec supports connecting to multiple containers in one workspace by placing per-service configs at .devcontainer/<name>/devcontainer.json, each pointing at a shared docker-compose.yml. devcontainer-mcp supports this pattern end-to-end:
Discovery โ devcontainer_list_configs returns every config it finds (root .devcontainer.json, .devcontainer/devcontainer.json, and each .devcontainer/*/devcontainer.json) with its kind (image / dockerfile / compose), service name, and absolute path.
Targeting โ Every devcontainer tool (up, exec, build, stop, remove, status, read_config, file_*) accepts an optional config parameter pointing at a specific devcontainer.json. Single-container workflows continue to work unchanged โ config defaults to whatever the devcontainer CLI auto-detects.
Ambiguity handling โ When a workspace has multiple configs and no config is provided, lookup-style tools (status, exec, stop, remove, file_*) return a structured Ambiguous result listing every matching container so the agent can pick the right one. status reports this as {"state":"Ambiguous","candidates":[...],"hint":"..."}.
Robust container matching โ Sibling compose containers are identified via com.docker.compose.service + com.docker.compose.project.config_files (not the unreliable devcontainer.local_folder label, which is only stamped on the first container).
Development
This project eats its own dogfood โ development happens inside its own devcontainer.
bash
# Using the devcontainer CLI
devcontainer up --workspace-folder .
devcontainer exec --workspace-folder . cargo build --workspace
devcontainer exec --workspace-folder . cargo test --workspace
devcontainer exec --workspace-folder . cargo build --release -p devcontainer-mcp
# Or using DevPod
devpod up . --id devcontainer-mcp --provider docker --open-ide=false
devpod ssh devcontainer-mcp --command"cd /workspaces/devcontainer-mcp && cargo build --workspace"