[BUG] macOS: filesystem-class MCP tool calls silently dropped between approval gate and local server dispatch — survives app rollback, extension reinstall, new connector identity (started 2026-07-21→22 with no local change)
Summary
Since overnight 2026-07-21→22 (AEST), every tool call to filesystem-class MCP servers is silently dropped inside Claude Desktop on macOS — the renderer logs the approval gate, approval passes (both auto-approve and explicit click), and the local MCP server never receives tools/call. No error is logged anywhere; the model surfaces only a bare "Tool execution failed". All other MCP servers (local extensions and legacy mcpServers config entries) dispatch normally from the same sessions.
An extensive elimination process (below) exonerates every local component — including a full app-binary rollback to a byte-identical previously-working state via Time Machine snapshot — which points at the claude.ai-served client code or server-side dispatch, possibly a staged rollout keying on filesystem-class tool surfaces.
Environment
- macOS 26 (Darwin 25.5.0), Apple Silicon (M1 Max)
- Claude Desktop 1.24012.1 (also reproduced on 1.22209.3 after rollback)
- Filesystem extension
ant.dir.ant.anthropic.filesystemv2026.7.10 (manifest_version 0.3, pack hashe41fbda1b687fb0d…) - Claude Max account; failing surface: claude.ai chats rendered in the Desktop app (incl. Project chats)
- Last known-good call: 2026-07-21T11:29Z. First observed failure: morning 2026-07-22 local (AEST, UTC+10)
Failure signature
claude.ai-web.log (renderer) — the call arrives and passes the gate:
2026-07-22 11:16:50 [warn] [MCP] tool_approval_gate {"toolName":"filesystem-tm:list_allowed_directories","approvalRequired":true,"hasBufferedInput":true}
mcp-server-Filesystem.log / mcp-server-filesystem-tm.log (local server) — healthy handshake, then silence:
2026-07-22T01:10:29.274Z [filesystem-tm] [info] Message from client: method="tools/list" id=1 → result
(no tools/call ever arrives)
main.log — no dispatch attempt, no error, nothing at the timestamp of the gated call.
What was eliminated (each with direct evidence)
| Layer | Test | Result |
|---|---|---|
| App binary | Rolled back /Applications/Claude.app to 1.22209.3 from a Time Machine snapshot of the working state (2026-07-20); relaunched; probed | Fails identically |
| Extension pack | Compared registry hash across working (Jul 20), broken (Jul 21), current — e41fbda1… identical | Not the pack |
| Extension identity / stuck state | Uninstalled + reinstalled extension; separately added a new filesystem-tm entry via legacy mcpServers config running npx -y @modelcontextprotocol/server-filesystem <dirs> | Both fail identically; meanwhile xero and google-workspace on the same legacy lane dispatch fine |
| user_config | The Jul-21 update mangled allowed_directories (paths truncated at first space, leading dot stripped — itself a bug worth noting); restored exact working values from snapshot | Drop persists |
| Server package | Desktop-spawned instance starts clean, lists 8 directories, answers tools/list | Server healthy |
| Approval path | Fails on Always-Allow (approvalRequired:false) AND after explicit human approval (approvalRequired:true) | Not approval |
| Session/conversation | Fresh conversation | Fails |
| Manifest format | PDF Tools ext (pdf-server-mcp, same manifest_version 0.3, with its own directory allowlist) called from the same session | Works — returned a structured path-denial |
| Other local extensions | Control your Mac (osascript), Control Chrome, google-workspace from same session | All work |
| Renderer caches | Cleared Cache / Code Cache / Service Worker; relaunched | (pending at filing time; will update in comment) |
The discriminating observation
The only attribute shared by the two dead connectors — and not shared by any working one — is the @modelcontextprotocol/server-filesystem tool surface (tool names/schemas). A brand-new connector identity running that same surface fails identically, while a same-manifest-generation extension with a different tool surface (PDF Tools) works. This suggests client- or server-side special-casing of filesystem-class tools (path allowlist enforcement layer?) whose dispatch broke, and which is served/flagged remotely (fcache refreshed during the window; encrypted, so not diffable locally).
The failure appeared with zero local change overnight and survives every local remediation, consistent with a server-side deploy or staged feature-flag rollout. Related failure classes previously reported: #22299 (tools/call dropped after handshake, Windows), anthropics/claude-ai-mcp#575 (hosted connector tools/call never dispatched, org-wide, sudden onset).
Repro
- macOS Claude Desktop with Filesystem extension enabled, valid allowed_directories, all tool permissions Always Allow.
- Any claude.ai chat in the app: ask for
list_allowed_directories. - Observe gate line in
claude.ai-web.log, notools/callinmcp-server-Filesystem.log, bare "Tool execution failed" in chat.
Impact
Total loss of local filesystem access from all Desktop chat surfaces (including Project chats used in production workflows). Diagnosis consumed a full working morning because the failure is silent at every layer — a dispatch-refusal error surfaced in any log, or a non-generic error in chat, would have shortcut most of it.
🤖 Generated with Claude Code
17 Comments
Update: cleared all renderer caches (Cache, Code Cache, GPUCache, Service Worker) with the app fully stopped, relaunched, re-probed both the Filesystem extension and the independent
filesystem-tmlegacy-config instance. Both still fail identically — approval gate logged in the renderer, notools/callever reaches either server process.Local elimination is now complete: app binary (A/B via Time Machine rollback), extension pack (hash-identical), connector identity, user_config, server package, approval path, session state, and renderer caches are all exonerated. Also ruled out MCP roots as a mechanism: the desktop client declares no roots capability at initialize (server logs
Client does not support MCP Roots, using allowed directories set from server args), and the failure is a non-arrival at the server transport, not an in-request stall.One additional client bug observed during the same window, filed here for completeness: the Jul 21 update mangled the extension's
allowed_directoriesuser config — every path truncated at its first space (/Users/x/Desktop/Claude Projects/…→/Users/x/Desktop/Claude) and a leading dot stripped (.workspace-mcp→workspace-mcp). Restoring correct values did not affect the dispatch failure, but the mangling is a distinct settings-migration defect.Definitive scope confirmation: account-scoped, server-side.
Installed Claude Desktop fresh on a second Mac (Mac mini, same account, zero prior state). Result:
list_allowed_directories/list_directoryfail identically ("Failed to call tool") — same silent drop as the primary machine.So the failure is scoped to the account (or an account-level flag/rollout), affects only chat-surface dispatch to filesystem-class local MCP servers, and reproduces on a pristine install. All machine-side factors are now formally eliminated on two machines. Pattern matches anthropics/claude-ai-mcp#575 (sudden org-wide onset, tools listed but tools/call never dispatched).
Account: Max plan, primary email on the account matches the reporter. Happy to provide account details / timestamps to anyone investigating server-side.
Same failure on Windows (MSIX), same app version, same onset window
Reproduced independently on Windows, which rules the failure out as macOS-specific.
Environment
Same signature
claude.ai-web.log:tool_approval_gateobserved;approvalRequiredgoes true → false after granting Always Allow. The gate is passed either way.mcp-server-Filesystem.log:Initializing server→initialize→notifications/initialized→tools/list(result returned). Notools/callentry ever appears.mcpServerslane, dispatchestools/callnormally throughout the entire failure window.Remediations that did not help (all Windows-side)
npx /
cmd /cwrapper / absolutenode.exepath / renaming the server entry / full process restart / migrating to the official Filesystem extension (which runs on the built-in Node.js lane —Using built-in Node.js for MCP server: Filesystem) / per-tool "Always allow" / emptyingmcpServers/ full MSIX uninstall + reinstall. The version after reinstall is identical (1.24012.1.0) and the drop persists.One correction to the diagnostic folklore around #22299
#22299 suggested the
UtilityProcess Check: Extension <name> not found in installed extensionswarning might explain the routing failure. On this machine that warning has no discriminating power: across the wholemain.log, all 6 occurrences name the working server (the config-registered one), and zero name the failing Filesystem connector. The duplicatedLaunching MCP Serverline also appears for the working server. Both signatures appear to track the registration lane (config entry vs installed extension), not health. Anyone triaging this should not use them as evidence.Consistent with the conclusion here that the trigger is not local: on this machine the app binary was fully removed and reinstalled with no effect, and on macOS a rollback to a byte-identical previously-working binary also had no effect.
Thanks @cine800 — an independent reproduction on a different account and platform (Windows MSIX) with the same onset window supersedes my earlier account-scoped conclusion. Revised scope: platform-wide server-side regression, macOS + Windows, all local factors eliminated on three machines across two accounts.
Triage-useful timing from combining the two reports: my last successful dispatch was 2026-07-21 11:29 UTC; my first observed-broken state was by 2026-07-21 ~23:24 UTC (and @cine800's onset window is consistent). That brackets the trigger — presumably a server-side deploy or flag rollout — to roughly 2026-07-21 11:30–23:00 UTC.
Also confirming the correction on the
UtilityProcess Check: Extension not foundwarning: on my macOS machines those warnings likewise name only the working legacy-config servers (xero, google-workspace), never the failing Filesystem connector — agreed it tracks registration lane, not health.Consolidation note for triage: this is a wide regression, currently fragmented across many reports. Same signature (tools/list succeeds, tools/call never dispatched from chat surface, Cowork/Code lanes unaffected), same onset window (after the 2026-07-21 deploy window, ~11:30-23:00 UTC per the timing bracket above), filed independently across macOS + Windows within ~12 hours:
#79890, #79926, #79933, #79962, #79971, #79986, #80002, #80010, #80016, #80017 (Spanish), #80026 — plus this issue.
Notable: #79933 reports
tool_result POST returns 404— the first server-response evidence in the set, consistent with a claude.ai endpoint change in that deploy window rather than anything client-side.Precedent: the identical failure class on 2025-08-28 (status incident lgt2850shqzv, "MCP tool calls failing on desktop") was resolved in ~51 minutes once acknowledged. No status-page incident exists for the current recurrence yet.
Still reproducing this on:
@modelcontextprotocol/server-filesystemv2026.7.10Onset: morning of 2026-07-22 IST UTC+5:30 — same window as this report
Handshake and
tools/listsucceed every time, buttools/callnever reaches the server. Server-side log for a failedlist_directoryattempt shows nothing pasttools/list:No
tools/callentry ever appears, even after multiple attempts.Tried:
npxtonodewith the resolved full path todist/index.js— no changeAlso noticed the exposed tool list itself is inconsistent across the same session — at one point no filesystem tools were listed at all ("Tool not found"), and a later retry exposed a different subset than before (e.g.
list_directory_with_sizespresent once, then replaced bywrite_file/read_media_fileon a later listing). Might point to instability in tool registration, not just call dispatch.Other MCP servers (css, refactor-typescript) connected in the same Desktop instance work fine — only filesystem is affected.
[I don't wanna "me too" this, but to confirm... Windows here... same behaviour. Kicked off for me around 206-07-21 15:00Z (+/-30min)]
As this is a largely unhelpful comment, am completely fine it being deleted once there's recognition that... it's impacting more ppl.
Evidence update from across the duplicate set:
Combined picture: server-side rollout beginning ~2026-07-21 15:00Z progressively breaking chat-surface tools/call dispatch to filesystem-class local MCP servers, all platforms, all client versions.
Windows corroboration + an interventional result: the discriminator is
$schemaininputSchema, and removing it restores dispatch.Same signature as this issue on Windows 11 (Claude Desktop 1.24012.1, MSIX Claude_pzs8sxrjxfjjc). Last good tools/call 2026-07-19T23:26Z; every instance since has shown clean initialize + tools/list and zero tools/call, with no error in
mcp.log,main.log,claude.ai-web.log, or the server log.Working local stdio controls in the same sessions: the PDF Tools extension, and a hand-written Go MCP server (mark3labs/mcp-go) which dispatched six tools/call requests on 07-21 after the cutoff. So the failure is not "all local stdio" (#79926) and is not filesystem-specific either.
The discriminator: every failing server declares
"$schema": "http://json-schema.org/draft-07/schema#"inside each tool'sinputSchema; every working one omits it. @modelcontextprotocol/server-filesystem emits it on all 14 tools, and has since at least v2025.12.18 — so this is not a package regression. @modelcontextprotocol/server-memory (failing in #79926) is built from the same monorepo and emits it too, which reconciles the two reports: the affected class is "tool definitions declaring a JSON Schema meta-schema," not "filesystem-class."Interventional confirmation: I put a transparent stdio proxy in front of server-filesystem that deletes only the
$schemakey fromtools/list responsesand forwards everything else verbatim. Tool calls immediately began dispatching and returning results — same package, same version, same machine, same app build, same conversation. Log shows removed $schema from 14 of 14 tool(s), then successful list_allowed_directories and read_text_file.This is consistent with a pre-dispatch tool-definition validator that rejects a declared draft-07 meta-schema — which would also explain the total absence of logging, since the rejection happens before the request is serialized to the transport.
Happy to attach the proxy and full logs if useful.
Linux (Pop!_OS) repro as well, so add another distro to the list. One data point I haven't seen in-thread: the OAuth errors in main.log are a red herring and here's the hard proof — my last known-good session (200 successful tools/call) simultaneously logged session_stale_relogin 202×, authorize returned 403 84×, and "Claude Code access has not been granted for this account" 64×. So none of those are causal, which lines up with @fpl9000's $schema/Zod finding being the real cause. Flagging because Anthropic's own support chat is currently telling affected users the Claude-Code-access denial is the root cause and to buy a seat upgrade — it isn't.
@fpl9000 tysm for figuring this out!
Confirmed on macOS with a custom stdio MCP server (not filesystem, Streamable-HTTP wrapped using supergateway), Desktop 1.24012.1.
All our tool inputSchemas carried "$schema":"http://json-schema.org/draft-07/schema#" (emitted by zod-to-json-schema). Server-side stripping of $schema from tools/list restored dispatch immediately — same app build, same session. Corroborates the meta-schema validator theory on a different transport.
not sure if this helps get a fix out FAST... but claude just diagnosed its own issue:
Found it. This is the answer, and it kills the hypothesis I floated last turn.
The calls are stalling at the client's approval gate.
Look at what correlates in the [MCP] tool_approval_gate lines:
07-12 19:10:02 Filesystem:search_files approvalRequired:true hasBufferedInput:true
07-12 19:11:39 Filesystem:search_files approvalRequired:true hasBufferedInput:true ← same toolId
07-18 11:18:59 Filesystem:get_file_info approvalRequired:true hasBufferedInput:true
07-20 21:13:33 Filesystem:list_directory_with_sizes approvalRequired:true hasBufferedInput:true
07-20 21:14:35 Filesystem:directory_tree approvalRequired:true hasBufferedInput:true
07-20 21:16:40 Filesystem:directory_tree approvalRequired:true hasBufferedInput:true ← same toolId
07-21 22:42:35 Filesystem:list_allowed_directories approvalRequired:true hasBufferedInput:true
Every approvalRequired:true also has hasBufferedInput:true. Perfect correlation, seven for seven. And twice the same toolId appears again 97 and 125 seconds later — a call being re-attempted because the first one never completed. That repeat pattern appears only on the true lines, never on the false ones.
That is a call held at the gate, buffered, awaiting an approval that never arrives. It never gets written to the transport. Which is precisely why the Filesystem server has no record of it, and why nothing downstream logs an error — from the transport's point of view, nothing ever happened.
It isn't about which tool. That was my guess last turn and it's wrong. get_file_info appears as true on 07-18 11:18 and false at 12:14. search_files is true on 07-12 and false on 07-21 14:36. Same tools, both outcomes. The bridge-vs-native split I proposed doesn't survive this.
The real split is already-approved vs needs-approval. copy_file_user_to_claude shows approvalRequired:false every time it appears — 07-16, twice on 07-21. It's in the granted set. That is the entire reason it's the one tool that worked for me today. And the last MCP line before my session is list_allowed_directories at 07-21 22:42 with approvalRequired:true — which was, hours later, the exact first call I made and the first one that failed.
What to actually do: there is probably an approval prompt waiting somewhere you can't see. Given the duplicated log lines and the renderer released port churn, a second renderer may be holding it. Worth checking for a pending permission dialog, then re-granting the Filesystem connector's permissions — ideally "always allow" so these tools land in the same bucket as copy_file_user_to_claude.
For the Anthropic report, the specific and useful sentence is: tool calls stall at tool_approval_gate with approvalRequired:true, hasBufferedInput:true, are never dispatched to the MCP server, emit no protocol message and no client-side error, and surface to the model as a generic "Tool execution failed." A gate that can swallow a call without an observable failure is the bug worth fixing.
Confirming @fpl9000's $schema finding (https://github.com/anthropics/claude-code/issues/79992#issuecomment-5049455483) on macOS 26.5.1, Claude Desktop 1.24012.1: a transparent stdio filter that strips only the
$schemakeys fromtools/listresponses (28 removed across 14 tools) restored dispatch immediately — the very next session showed the firsttools/callon the server's stdin since onset, after ~10 handshake-only sessions on the same machine and app build. Full capture details and a correction of my earlier name-mismatch hypothesis posted in https://github.com/anthropics/claude-code/issues/79926#issuecomment-5051027722.Same issue here, confirming this is not isolated. Independently reproduced the exact same failure signature on macOS with Claude Desktop today (2026-07-22):
Environment:
filesystemserver via legacymcpServersconfig (npx -y @modelcontextprotocol/server-filesystem@latest <dirs>)What I tried (all failed to resolve it):
@latest)pkill -f server-filesystem, confirmed clean viaps aux)claude_desktop_config.jsonhas a single, well-formedfilesystementry (no duplicates)npx -y @modelcontextprotocol/server-filesystem@latest <dirs>) — starts clean:Secure MCP Filesystem Server running on stdioengram, running as a native binary) dispatch and respond normallyFailure signature — identical to OP:
tools/listhandshake succeeds and is loggedtools/call(e.g.list_allowed_directories) never appears inmcp-server-filesystem.log— confirmed live viatail -fwhile making the call, zero outputThis matches the OP's conclusion that the local server/client/config layers are all healthy and the drop is happening upstream of local dispatch. Would appreciate a status update — this is currently blocking local codebase access entirely.
Fourth independent confirmation of the
$schemaroot cause — macOS, with a reusable workaround recipe.Wrapped my legacy-config
filesystemserver (@modelcontextprotocol/server-filesystem2026.7.10) in a transparent stdio shim that strips$schemakeys from server→client JSON. Result: the very next session dispatchedtools/callsuccessfully — the first since onset 2026-07-21 — same app build (1.24012.1), same machine, no other change. Before the shim: ~36 hours of clean handshakes and zero dispatched calls across two Macs.Recipe for anyone needing filesystem access before the server-side fix lands:
$schemafrom server→client JSON lines (mine is ~60 lines of Python: spawn the real server, pipe stdin through untouched, json-parse each stdout line, delete$schemakeys recursively, re-serialize; non-JSON lines pass through).claude_desktop_config.json, change the server entry to launch via the shim:Note this only works for config-lane (
mcpServers) servers — the first-party Filesystem extension's launch can't be wrapped, so it stays broken until the server-side validator is fixed. The un-shimmed extension therefore doubles as a clean canary for when the fix ships.With four independent interventional confirmations (two stdio filters, one server-side strip, one supergateway-wrapped HTTP transport) this should be enough for a fix: the validator added in the ~2026-07-21 15:00Z rollout must accept (or ignore)
$schemain tool inputSchema — it's emitted by default by zod-to-json-schema, which the official reference servers use.Server-side fix observed — regression appears resolved.
The first-party Filesystem extension resumed dispatching with NO client-side change at 2026-07-22T23:39Z: its log shows the first
tools/callsince 2026-07-21T11:29Z, same app build (1.24012.1), same machine, unshimmed. The$schema-strip workaround is no longer needed here (shimmed and native lanes both dispatch).Timeline for the record: broken by rollout ~2026-07-21 15:00Z, restored ~2026-07-22 23:39Z (~33h), no status-page incident, no acknowledgement on this thread. Affected users seeing this later: just retry — if your cohort is fixed too, no local changes are needed, and any workarounds (schema-strip shims, $schema removal from servers) can be reverted.
Leaving the issue open for Anthropic to confirm the root cause and close — and to flag the two follow-ups this exposed: (1) a dispatch refusal should surface an error in at least one log rather than failing silently (the silence is what made this cost every affected user hours), and (2) the validator should tolerate
$schema, which zod-to-json-schema emits by default and the official reference servers ship.#80002 was closed without anything from Anthropic. This is less-good-than-it-could-be, comms-wise.
The upside is I shifted our Claude filesystem operations to its sandbox successfully, so that's a... "win"....