Docs say `claude_desktop_config.json` MCP servers "will not appear in the Code tab," but the desktop app injects them into Code sessions

Resolved 💬 2 comments Opened Jun 1, 2026 by privacyguy123 Closed Jun 22, 2026

Preflight Checklist

  • [x] I have searched existing issues and this hasn't been reported yet
  • [x] This is a single bug report
  • [x] I am using a recent build (Claude Desktop 1.9659.2 / engine 2.1.156)

Summary

The Desktop documentation states that MCP servers in claude_desktop_config.json are isolated from the Code tab, but in practice the desktop app injects them into Code-tab sessions at runtime. The documented contract and the actual behavior disagree.

Environment

  • Claude Desktop (Windows): 1.9659.2 (x64 / MSIX)
  • Bundled Claude Code engine: 2.1.156
  • OS: Windows 10 Pro 19045
  • Also reproduces on macOS per #53281 (desktop 1.4758.0 / binary 2.1.119), so this is not Windows-specific.

What the docs say

Desktop reference -> Shared configuration:

MCP servers configured for the Claude Desktop chat app in claude_desktop_config.json are separate from Claude Code and will not appear in the Code tab. To use MCP servers in Claude Code, configure them in ~/.claude.json or your project's .mcp.json file.

What actually happens

MCP servers defined only in claude_desktop_config.json are present and callable in Code-tab sessions.

Repro

  1. Add a stdio MCP server to claude_desktop_config.json only (do not add it to ~/.claude.json or any .mcp.json).
  2. Start a Code-tab session and list/call MCP tools.
  3. The server's tools are available (e.g. mcp__<server>__*) even though no Claude Code file config references it.

In my case winget-mcp and a stdio github server exist only in claude_desktop_config.json, yet both are live in the Code tab.

Mechanism (from app bundle + live process inspection)

  • The Code engine is launched by the desktop app as an SDK subprocess:

claude.exe --output-format stream-json --input-format stream-json --setting-sources=user,project,local ... — with no --mcp-config flag, so the servers are not arriving via a flag or settings file.

  • resources/app.asar parses claude_desktop_config.json (including validation and user-facing "...not valid MCP server configurations and were skipped" dialogs) and pushes servers to the running engine over the SDK control protocol:

query.setMcpServers({ ...claudeJsonMcpServers, ...activeMcpServers }) / replaceRemoteMcpServers.

  • Independently corroborated by the main.log excerpt in #53281:

[CCD] [replaceRemoteMcpServers] Calling SDK with N total servers { serverNames: [ ...chat connectors..., 'ccd_session', 'ccd_directory', ... ] }.

Why it matters

  • Contradicts the documented contract and causes confusion about where MCPs should be configured for the Code tab.
  • Least-privilege / security: a coding agent that runs shell commands silently inherits every Chat MCP server, including ones holding plaintext credentials (e.g. a stdio GitHub server with a PAT stored in claude_desktop_config.json). There is no documented way to opt out.
  • Duplicate toolsets: when the same service is configured both as a chat MCP and as a Code plugin/connector, the Code tab loads it twice.

Request

Please reconcile the docs with the behavior. If the injection is intended (it appears deliberate), document it, and consider an opt-in/toggle so users can keep Chat MCP servers out of Code-tab sessions.

View original on GitHub ↗

This issue has 2 comments on GitHub. Read the full discussion on GitHub ↗