The Docker Desktop UI is fine for setting up your first profile. For the second one, or the tenth, or for scripting it into a repo bootstrap, I want the Docker MCP Toolkit CLI. This post is a reference for the docker mcp commands I actually use, grouped by component, each with a one-line description.
If you haven’t met catalogs, profiles, and the gateway yet, start with Docker MCP Toolkit: Catalogs, Profiles, and the Gateway. This post assumes you know what they are.
Everything here was run against Docker Desktop with docker mcp v0.43.3. Commands work the same in PowerShell and bash, except the multi-line ones: swap \ for a backtick in PowerShell.
Basics
1
2
3
| docker mcp version # Show the Toolkit CLI version
docker mcp --help # List all command groups
docker mcp <group> --help # Help for one group, e.g. docker mcp profile --help
|
Catalogs
1
2
3
4
5
6
7
8
9
10
11
| # List the catalogs you have locally
docker mcp catalog ls
# List every server in Docker's catalog, with type and tool count
docker mcp catalog server ls mcp/docker-mcp-catalog
# Show catalog details
docker mcp catalog show mcp/docker-mcp-catalog
# Pull a catalog your team published
docker mcp catalog pull registry.example.com/mcp/company-tools:latest
|
The name in the server ls output (playwright, github-official, context7) is the server ID used in every command below.
Profiles
1
2
3
4
5
6
7
8
9
10
11
| # Create an empty profile
docker mcp profile create --name web_dev
# List profiles (ID and name)
docker mcp profile list
# Show a profile's servers, config, tools, and snapshot
docker mcp profile show web_dev
# Delete a profile and all its settings (no undo)
docker mcp profile remove web_dev
|
Gotcha: --name blog-demo creates a profile with the ID blog_demo. Every other command needs the ID, so blog-demo fails with profile blog-demo not found. Use underscores in names to avoid the mismatch.
Start from a template
1
2
3
4
5
6
7
8
| # List starter templates (ai-coding, dev-workflow, terminal-control)
docker mcp template list
# Create a profile from a template
docker mcp template use ai-coding
# Create it and connect a client in one step
docker mcp template use ai-coding --connect claude-code
|
Servers in a Profile
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| # Add servers from a catalog (repeat --server for several)
docker mcp profile server add web_dev \
--server catalog://mcp/docker-mcp-catalog/github-official \
--server catalog://mcp/docker-mcp-catalog/playwright
# Add any MCP-speaking Docker image
docker mcp profile server add web_dev --server docker://registry.example.com/mcp/internal-api:latest
# Add a server defined in a local YAML file
docker mcp profile server add web_dev --server file://./my-server.yaml
# List servers across all profiles
docker mcp profile server ls
# List servers in one profile
docker mcp profile server ls --filter profile=web_dev
# Remove servers (repeat --name for several)
docker mcp profile server remove web_dev --name playwright
|
Server URI formats:
| URI | Source |
|---|
catalog://<catalog-ref>/<server-id> | Server from an OCI catalog |
docker://<image>:<tag> | Any Docker image |
https://<url>/v0/servers/<uuid> | MCP community registry |
file://<path> | Local YAML/JSON definition |
Server Configuration
1
2
3
4
5
6
7
8
| # Set a config value (keys are defined by each server)
docker mcp profile config web_dev --set <server-id>.<key>=<value>
# Show all config values in a profile
docker mcp profile config web_dev --get-all
# Delete a config value
docker mcp profile config web_dev --del <server-id>.<key>
|
1
2
3
4
5
6
7
8
9
10
11
| # Disable specific tools (<server>.<tool>)
docker mcp profile tools web_dev --disable github-official.create_repository
# Enable specific tools
docker mcp profile tools web_dev --enable github-official.list_pull_requests
# Disable every tool from a server
docker mcp profile tools web_dev --disable-all github-official
# Enable every tool from a server
docker mcp profile tools web_dev --enable-all github-official
|
To allow only a few tools from a big server, run --disable-all first, then --enable the ones you want.
Secrets and OAuth
1
2
3
4
5
6
7
8
9
10
11
| # Store a secret in the OS keychain (piped, so it stays out of shell history)
cat token.txt | docker mcp secret set context7.api_key
# List stored secrets (names only)
docker mcp secret ls
# Remove a secret
docker mcp secret rm context7.api_key
# Manage OAuth authorizations for remote servers
docker mcp oauth --help
|
Security note: Avoid docker mcp secret set NAME=value in an interactive shell. The value ends up in your history file. Pipe it in from a file or a password manager instead, and delete any temporary file afterwards.
1
2
3
4
5
6
7
| docker mcp tools ls # List tools the gateway exposes
docker mcp tools count # Count them (handy for context-budget checks)
docker mcp tools inspect <tool> # Show a tool's schema
docker mcp tools call <tool> key=value # Call a tool directly, no AI client needed
# Example: ask the gateway's catalog search for Postgres servers
docker mcp tools call mcp-find query=postgres
|
The MCP Gateway
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
| # Run the gateway over stdio with a profile (what clients launch)
docker mcp gateway run --profile web_dev
# Validate a profile: pull, verify, and list tools without serving
docker mcp gateway run --profile web_dev --dry-run
# Run against a custom catalog instead of a profile
docker mcp gateway run --catalog registry.example.com/mcp/company-tools:latest
# Enable specific servers from a catalog without a profile
docker mcp gateway run --catalog <oci-ref> --servers github-official --servers playwright
# Give heavy servers more resources (defaults: 1 CPU, 2Gb)
docker mcp gateway run --profile web_dev --cpus 2 --memory 4Gb
# Block tools from reaching forbidden network resources
docker mcp gateway run --profile web_dev --block-network
# Keep containers alive between calls (stateful servers)
docker mcp gateway run --profile web_dev --long-lived
# Serve over HTTP instead of stdio
docker mcp gateway run --profile web_dev --transport streaming --port 8811
|
--dry-run is the one I run most. It shows exactly which images are used, the docker run flags each server gets, and how many tools each one exposes.
Security note: With --transport streaming, the gateway uses the MCP_GATEWAY_AUTH_TOKEN environment variable to protect localhost. Don’t add --allow-unauthenticated, and don’t bind --host 0.0.0.0 on a shared network. Leave --verify-signatures and --block-secrets on (both default to on).
Clients
1
2
3
4
5
6
7
8
9
| # Show which clients are connected, for this project and globally
docker mcp client ls
# Connect a supported client to a profile
docker mcp client connect vscode --profile web_dev
docker mcp client connect claude-code --profile web_dev
# VS Code writes a per-user file into the project; keep it out of git
echo ".vscode/mcp.json" >> .gitignore
|
For a client that isn’t supported, add this entry to its MCP config (most JSON-based clients):
1
2
3
4
5
6
7
8
9
| {
"servers": {
"MCP_DOCKER": {
"command": "docker",
"args": ["mcp", "gateway", "run", "--profile", "web_dev"],
"type": "stdio"
}
}
}
|
Claude Desktop uses mcpServers and drops type:
1
2
3
4
5
6
7
8
| {
"mcpServers": {
"MCP_DOCKER": {
"command": "docker",
"args": ["mcp", "gateway", "run", "--profile", "web_dev"]
}
}
}
|
Verify from Claude Code:
1
2
| claude mcp list
# MCP_DOCKER: docker mcp gateway run - ✓ Connected
|
Sharing Profiles
1
2
3
4
5
6
7
8
9
10
11
12
| # Push a profile to an OCI registry
docker mcp profile push web_dev registry.example.com/profiles/web-dev:v1
# Pull a shared profile
docker mcp profile pull registry.example.com/profiles/web-dev:v1
# Export to a file for version control
mkdir -p .docker
docker mcp profile export web_dev .docker/mcp-profile.json
# Import after cloning
docker mcp profile import .docker/mcp-profile.json
|
Credentials are never exported. Each teammate sets their own secrets after pulling or importing.
Custom Catalogs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| # Copy Docker's catalog as a starting point
docker mcp catalog tag mcp/docker-mcp-catalog registry.example.com/mcp/company-tools:latest
# Remove servers your org hasn't approved
docker mcp catalog server remove registry.example.com/mcp/company-tools:latest --name <server-id>
# Add your own private server images
docker mcp catalog server add registry.example.com/mcp/company-tools:latest \
--server docker://registry.example.com/mcp/internal-api:latest
# Or build a catalog from scratch with only chosen servers
docker mcp catalog create registry.example.com/mcp/data-tools:latest \
--title "Data Analysis Tools" \
--server catalog://mcp/docker-mcp-catalog/sequentialthinking \
--server catalog://mcp/docker-mcp-catalog/brave
# Inspect it
docker mcp catalog show registry.example.com/mcp/data-tools:latest
# Publish it for the team
docker mcp catalog push registry.example.com/mcp/data-tools:latest
|
A Five-Command Setup
If you only want the short version, this takes you from nothing to a working, sandboxed setup in Claude Code:
1
2
3
4
5
6
7
| docker mcp profile create --name research
docker mcp profile server add research \
--server catalog://mcp/docker-mcp-catalog/context7 \
--server catalog://mcp/docker-mcp-catalog/sequentialthinking
docker mcp gateway run --profile research --dry-run
docker mcp client connect claude-code --profile research
claude mcp list
|
Create, fill, validate, connect, verify. For why each piece exists, see the overview post. For every flag, see Docker’s CLI reference.