Skip to content

Gateway leaks containers and zombie processes under concurrent tool calls #483

@manuelturpin

Description

@manuelturpin

Description

The docker mcp gateway (v0.34.0) leaks containers and accumulates zombie processes when handling concurrent MCP tool calls from multiple background agents. A single Claude Code session running 10 parallel agents produced 180+ orphaned containers and 526 zombie processes, bringing the host machine to 100% CPU.

Environment

  • docker-mcp: v0.34.0
  • Docker Desktop: macOS (Darwin 25.3.0)
  • Client: Claude Code CLI v2.1.110
  • MCP servers registered: 9 (github-official, brave, fetch, playwright, context7, etc.)

Steps to reproduce

  1. Connect docker mcp to Claude Code (docker mcp client connect claude-code)
  2. Register multiple MCP servers including github-official, brave, fetch
  3. Start a Claude Code session
  4. Launch 10+ background agents that make concurrent MCP tool calls (brave_web_search, fetch) through the gateway

In my case this was triggered by a deep-research workflow dispatching 10 parallel agents, each making web searches and URL fetches simultaneously through the single gateway process.

Observed behavior

Container leak

The gateway creates a new Docker container per tool call but does not reuse or clean up containers under concurrent load. Over ~2 hours:

  • 180+ running containers of ghcr.io/github/github-mcp-server accumulated
  • Containers stay in "Up" state indefinitely
  • New containers keep being created even after the calling agents have finished

Zombie processes

The gateway process does not reap child processes:

Gateway PID 82681: 1475 open FDs, 726 children, 526 zombies

For comparison, 8 other gateway instances on the same machine (handling normal single-agent load) had 0 children and 0 zombies each:

Gateway 82681 (10 concurrent agents) : 1475 FDs, 726 children, 526 zombies
Gateway 2922  (normal usage)         :   22 FDs,   0 children,   0 zombies

Resource impact

  • Docker VM: 332% CPU (saturating 3+ cores)
  • kernel_task: 62% CPU (thermal throttling)
  • Host machine essentially unusable (idle < 3%)

Self-reinforcing loop

After killing all containers, the gateway immediately respawns new ones (~20 containers in 10 seconds). The only fix was to kill the gateway process itself.

Expected behavior

  1. The gateway should reuse containers across tool calls to the same MCP server, or implement a container pool
  2. Child processes should be properly reaped (no zombies)
  3. There should be a max concurrent containers limit
  4. Containers should be cleaned up when the calling session/agent finishes
  5. When the parent Claude Code session is idle (no pending tool calls), the gateway should not spawn new containers

Diagnostic data

Container labels (from docker run command observed via ps):

docker run --rm -i --init --security-opt no-new-privileges \
  --cpus 1 --memory 2Gb --pull never \
  -l docker-mcp=true \
  -l docker-mcp-tool-type=mcp \
  -l docker-mcp-name=github-official \
  -l docker-mcp-transport=stdio \
  -e GITHUB_PERSONAL_ACCESS_TOKEN \
  ghcr.io/github/github-mcp-server@sha256:5049daf...

Container creation rate (from docker ps timestamps):

15:11  — 39 containers created in 1 minute
15:12  — 68 containers created in 1 minute
15:13  — 11 containers
16:00  — 9 containers
16:01  — 22 containers
... continuous creation for 2+ hours

Process tree:

cmux → login → zsh → claude (PID 82364) → docker mcp gateway run (PID 82681)
                                            ├── 726 child docker-run processes
                                            └── 526 zombie processes

Related

Workaround

Kill the affected gateway process (kill <gateway-pid>). The Claude Code session survives and will spawn a fresh gateway on next MCP tool call. Then clean up orphaned containers:

docker rm -f $(docker ps -aq --filter "label=docker-mcp-name=github-official")

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions