Skip to content

feat(diagnostics): make MCPX_DOCKER_EXEC_NOT_FOUND runtime-aware (MCP-2909)#720

Merged
Dumbris merged 2 commits into
mainfrom
fix/mcp-2909-docker-exec-runtime-aware
Jun 19, 2026
Merged

feat(diagnostics): make MCPX_DOCKER_EXEC_NOT_FOUND runtime-aware (MCP-2909)#720
Dumbris merged 2 commits into
mainfrom
fix/mcp-2909-docker-exec-runtime-aware

Conversation

@Dumbris

@Dumbris Dumbris commented Jun 19, 2026

Copy link
Copy Markdown
Member

Summary

Makes the MCPX_DOCKER_EXEC_NOT_FOUND diagnostic runtime-aware so a user can self-resolve it.

A field report (ElevenLabs upstream, uvx runtime) hit this code because of a per-server isolation.image: "python:3.11" override — stock python:3.11 has no uvx (uv is a separate Astral tool), so docker run python:3.11 uvx … fails at exec time inside the container. The system behaved correctly, but the owner misattributed it to recent host-side docker PATH fixes (#697/#703/#714/#716/#717). That misdiagnosis is the signal: the static catalog message ("the image has no uvx/node") is too generic.

What changed (diagnostics-only)

  • ClassifierHints gains DockerCommand, DockerImageOverride, DockerDefaultImages. These are diagnostics-only — they never affect classification, only the user-facing message.
  • RuntimeAwareRemediation(code, hints) (new, internal/diagnostics/remediation.go) builds an enriched message for DockerExecNotFound that names:
    1. the detected runtime (uvx/npx/pipx/…),
    2. the recommended image (default_images[runtimeType]),
    3. and flags a per-server isolation.image override as the likely culprit when it differs from the runtime default.
  • DiagnosticError.Remediation carries the enriched string; the REST (internal/server/server.go) and status (internal/runtime/runtime.go) serializers prefer it over the static UserMessage when present.
  • The supervisor (classifierHints) populates the new hints from the server config + global default_images for Docker-isolated servers.
  • detectDockerRuntimeType is a small, side-effect-free mirror of core.DetectRuntimeType (the diagnostics package must not import upstream/core; same precedent as supervisor.usesDockerIsolation mirroring ShouldIsolate).
  • Docs: new docs/errors/MCPX_DOCKER_EXEC_NOT_FOUND.md + README index entry (the docsURL target previously 404'd).

Out of scope (per issue): image selection and TransformCommandForContainer are unchanged (correct since #477). A config-save/connect-time warning for override mismatch was declined by the owner.

Example enriched message

This uvx server's Docker image has no uvx interpreter, so the container could not start it. The per-server isolation.image override python:3.11 is the likely culprit — it differs from the recommended image for uvx. The recommended image for uvx is ghcr.io/astral-sh/uv:python3.13-bookworm-slim. Remove the per-server isolation.image override to inherit it, or pick an image that includes uvx.

Testing (TDD)

  • internal/diagnostics/classifier_domains_test.go: new TestRuntimeAwareRemediation_DockerExecNotFound (uvx-on-bare-python override, npx-no-override, no-command fallback, other-code no-op). Written failing first, then implemented.
  • go build ./..., go test ./internal/diagnostics/... ./internal/runtime/supervisor/... -race green.
  • golangci-lint (v2, .github/.golangci.yml) on touched packages: 0 issues.

Related MCP-2909

The static DockerExecNotFound catalog message ("the image has no
uvx/node") is too generic to self-resolve. A field report (ElevenLabs /
uvx) hit it because of a per-server `isolation.image: "python:3.11"`
override — stock python has no uvx — but the owner misattributed it to
recent host-side docker PATH fixes.

Enrich the remediation with per-server context: name the detected
runtime (uvx/npx/pipx/…), the recommended runtime-default image
(default_images[runtimeType]), and flag a per-server isolation.image
override as the likely culprit when it differs from the default.

- ClassifierHints gains DockerCommand / DockerImageOverride /
  DockerDefaultImages (diagnostics-only; never affect classification).
- RuntimeAwareRemediation(code, hints) builds the enriched message;
  DiagnosticError.Remediation carries it; the REST/status serializers
  prefer it over the static UserMessage when present.
- detectDockerRuntimeType mirrors core.DetectRuntimeType for display
  (diagnostics must not import upstream/core).
- Add docs/errors/MCPX_DOCKER_EXEC_NOT_FOUND.md + README index entry.

Image selection and TransformCommandForContainer are unchanged
(correct since #477) — this is diagnostics-only.

Related MCP-2909
@cloudflare-workers-and-pages

cloudflare-workers-and-pages Bot commented Jun 19, 2026

Copy link
Copy Markdown

Deploying mcpproxy-docs with  Cloudflare Pages  Cloudflare Pages

Latest commit: 99ce599
Status: ✅  Deploy successful!
Preview URL: https://1e834ce8.mcpproxy-docs.pages.dev
Branch Preview URL: https://fix-mcp-2909-docker-exec-run.mcpproxy-docs.pages.dev

View logs

…D page

Docusaurus broken-links check failed the docs build: ../docker-isolation.md
resolved to /docker-isolation.md (no such route). Use ../features/docker-isolation.md,
matching the sibling MCPX_DOCKER_IMAGE_PULL_FAILED page.

Related MCP-2909
@codecov-commenter

Copy link
Copy Markdown

⚠️ Please install the 'codecov app svg image' to ensure uploads and comments are reliably processed by Codecov.

Codecov Report

❌ Patch coverage is 28.57143% with 65 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
internal/diagnostics/remediation.go 42.62% 35 Missing ⚠️
internal/runtime/supervisor/supervisor.go 0.00% 22 Missing ⚠️
internal/runtime/runtime.go 0.00% 4 Missing ⚠️
internal/server/server.go 0.00% 4 Missing ⚠️

📢 Thoughts on this report? Let us know!

@github-actions

github-actions Bot commented Jun 19, 2026

Copy link
Copy Markdown

📦 Build Artifacts

Workflow Run: View Run
Branch: fix/mcp-2909-docker-exec-runtime-aware

Available Artifacts

  • archive-darwin-amd64 (28 MB)
  • archive-darwin-arm64 (25 MB)
  • archive-linux-amd64 (16 MB)
  • archive-linux-arm64 (14 MB)
  • archive-windows-amd64 (28 MB)
  • archive-windows-arm64 (25 MB)
  • frontend-dist-pr (0 MB)
  • installer-dmg-darwin-amd64 (21 MB)
  • installer-dmg-darwin-arm64 (19 MB)

How to Download

Option 1: GitHub Web UI (easiest)

  1. Go to the workflow run page linked above
  2. Scroll to the bottom "Artifacts" section
  3. Click on the artifact you want to download

Option 2: GitHub CLI

gh run download 27804766378 --repo smart-mcp-proxy/mcpproxy-go

Note: Artifacts expire in 14 days.

@mcpproxy-gatekeeper mcpproxy-gatekeeper Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

APPROVE — reviewed via Claude Code. Runtime-aware remediation message for existing MCPX_DOCKER_EXEC_NOT_FOUND; classifier UNCHANGED (no new/over-broad string-matching — per repo caveat), display-layer only, gated on code+DockerCommand!='' and fully nil-safe (supervisor hint chain guards srv/Isolation/snap.Config). Both render sites consistent; Remediation JSON omitempty (back-compat). go build clean, diagnostics+runtime tests pass (4 new subtests); internal/server FAILs are pre-existing E2E binary-path env, not this diff. MCP-2849.

@Dumbris Dumbris merged commit fbeee75 into main Jun 19, 2026
39 checks passed
@Dumbris Dumbris deleted the fix/mcp-2909-docker-exec-runtime-aware branch June 19, 2026 19:27
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants