From 472c0681594ccd137666fc2b87f4913d2e6cc5b0 Mon Sep 17 00:00:00 2001 From: xxxigm Date: Sun, 21 Jun 2026 14:54:02 +0700 Subject: [PATCH] fix(mcp): detect 'unknown method' phrasing in ping keepalive fallback A server that doesn't implement the optional 'ping' utility answers a keepalive ping with JSON-RPC method-not-found. _is_method_not_found_error latches that condition so the probe falls back to list_tools instead of reconnect-looping. The substring fallback only matched 'method not found' / '-32601' / 'not found: ping'. Servers that surface method-not-found as the common 'Unknown method: ' phrasing without a structural -32601 code (e.g. agentmemory's MCP server) slipped through, so the fallback never latched and the keepalive reconnect-looped every cycle. Add 'unknown method' to the substring fallback so the ping->list_tools keepalive fallback latches for these servers too. Fixes #50028. --- tools/mcp_tool.py | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/tools/mcp_tool.py b/tools/mcp_tool.py index 69917ec6a8a..e4448bacd25 100644 --- a/tools/mcp_tool.py +++ b/tools/mcp_tool.py @@ -415,6 +415,13 @@ def _is_method_not_found_error(exc: BaseException) -> bool: an empty result. Structurally inspect ``McpError.error.code`` first, then fall back to a substring match so detection survives SDK version drift and servers that surface the condition as a plain message. + + The substring fallback matters when a server reports method-not-found + without a structural ``-32601`` code (e.g. surfaced as a plain exception + string). Besides the canonical "method not found", many JSON-RPC + implementations phrase it as "Unknown method: " — agentmemory's MCP + server is one such case (#50028). Without matching that phrasing the + ping→list_tools fallback never latches and the keepalive reconnect-loops. """ # Structural: mcp.shared.exceptions.McpError carries ErrorData.code. err = getattr(exc, "error", None) @@ -427,6 +434,7 @@ def _is_method_not_found_error(exc: BaseException) -> bool: return ( str(_JSONRPC_METHOD_NOT_FOUND) in msg or "method not found" in msg + or "unknown method" in msg or "not found: ping" in msg )