Remove unused mcpserver.exceptions.ValidationError - #3199
Conversation
Never raised in v1 or v2, and it shadows pydantic.ValidationError. No-Verification-Needed: user opted out of review; dead-code deletion
| """Base error for MCPServer.""" | ||
|
|
||
|
|
||
| class ValidationError(MCPServerError): | ||
| """Error in validating parameters or return values.""" | ||
|
|
||
|
|
||
| class ResourceError(MCPServerError): |
There was a problem hiding this comment.
🔴 This PR removes the public symbol mcp.server.mcpserver.exceptions.ValidationError — a breaking change per the PR's own checklist — but does not add the required entry to docs/migration.md (AGENTS.md: breaking changes must be documented there). Add a line to the existing exceptions inventory in the FastMCP→MCPServer section noting ValidationError was removed and that callers should catch pydantic.ValidationError or drop the import.
Extended reasoning...
The gap. AGENTS.md states unconditionally: "Breaking changes (including those softened by a backwards-compatibility shim) must be documented in docs/migration.md", covering what changed, why, and how to migrate. This PR deletes the public class ValidationError from mcp.server.mcpserver.exceptions, and the PR description itself checks the Breaking change box ("Only for code importing a symbol the SDK never raised"). Yet the diff touches only src/mcp/server/mcpserver/exceptions.py — docs/migration.md is not updated.
Why it's breaking despite never being raised. The breaking surface is the import itself, not the raise. The symbol existed in v1's fastmcp/exceptions.py and in v2 up to this PR, so user code doing from mcp.server.mcpserver.exceptions import ValidationError — e.g. to catch it defensively alongside ToolError/ResourceError, or code mid-migration from v1's mcp.server.fastmcp.exceptions — now fails at import time with ImportError. "The SDK never raised it" is exactly the why that belongs in the migration entry; it is not an exemption from writing one.
Why existing docs don't cover it. Grepping docs/migration.md for ValidationError finds only references to pydantic's ValidationError (resource extra="forbid", elicitation, wire validation, etc.). None documents this removal. Meanwhile the guide already contains the exact inventory this entry belongs in: the FastMCP→MCPServer section's import list (around lines 664–668) enumerates ToolError, ResourceError, and MCPServerError as importable from mcp.server.mcpserver.exceptions. Per AGENTS.md's guidance to group related changes with existing sections rather than adding standalone ones, the removal note goes right there.
Step-by-step proof.
- A v1 user has
from mcp.server.fastmcp.exceptions import ToolError, ValidationError(defensive catch-all around tool invocation). - Following the migration guide, they rewrite the module path:
from mcp.server.mcpserver.exceptions import ToolError, ValidationError. - On a v2 build containing this PR, that line raises
ImportError: cannot import name 'ValidationError' from 'mcp.server.mcpserver.exceptions'. - They consult
docs/migration.md, search forValidationError, and find only pydantic-related entries — no explanation that the symbol was removed or what to do instead.
Impact and fix. Merging as-is leaves the v1→v2 migration guide concretely incomplete for an acknowledged breaking change, violating the repo's explicit "must". The fix is a one-line doc addition to the existing inventory, e.g.: ValidationError — removed; it was never raised by the SDK (v1 or v2) and only shadowed pydantic.ValidationError. Catch pydantic.ValidationError if that's what you meant, or drop the import.
Severity. Normal rather than nit because this isn't a stale-description mismatch — the code/docs state after merge violates a hard repo policy ("must be documented in docs/migration.md"), and the guide's whole purpose on the V2 branch is to be the complete record of the v1→v2 delta. All three verifiers independently confirmed with no refutations.
Deletes
ValidationErrorfrommcp.server.mcpserver.exceptions.Motivation and Context
It was never raised — not in v1's
fastmcp/exceptions.pyand not in v2 — and nothing in the SDK imports it. All it does is shadowpydantic.ValidationErrorfor anyone who imports it.How Has This Been Tested?
Grep for references across
src/,tests/,examples/,docs/; the only hit was the definition itself. ruff + pyright pass.Breaking Changes
Only for code importing a symbol the SDK never raised.
Types of changes
Checklist