fix(schemas): import from zod/v4 to match SDK's zod API#548
Merged
Conversation
The generated schemas compose with schemas imported from
@modelcontextprotocol/sdk/types.js (e.g. z.array(ContentBlockSchema)).
The SDK constructs its schemas via `import * as z from 'zod/v4'`, but
our generated schema.ts used `import { z } from "zod"` — which returns
the v3 API when the consumer has zod 3.25.x installed.
Mixing v3-created and v4-created schema instances throws at parse time
with errors like `keyValidator._parse is not a function` because zod v4
dropped the `_parse` / `_parseSync` internals that v3 wrappers call.
This was masked before #534 because zod was bundled — all schema
creation shared the same inlined zod copy. Externalizing zod exposed
the mismatch on consumers pinned to zod 3.x (e.g. anthropics/apps).
The `zod/v4` subpath is exported by both zod 3.25+ and zod 4.x, so the
existing peerDependency range `^3.25.0 || ^4.0.0` is preserved.
https://claude.ai/code/session_013xQUegrvVGct5xpqeSL5av
Contributor
PreviewPreview deployments for this PR have been cleaned up. |
@modelcontextprotocol/ext-apps
@modelcontextprotocol/server-basic-preact
@modelcontextprotocol/server-basic-react
@modelcontextprotocol/server-basic-solid
@modelcontextprotocol/server-basic-svelte
@modelcontextprotocol/server-basic-vanillajs
@modelcontextprotocol/server-basic-vue
@modelcontextprotocol/server-budget-allocator
@modelcontextprotocol/server-cohort-heatmap
@modelcontextprotocol/server-customer-segmentation
@modelcontextprotocol/server-debug
@modelcontextprotocol/server-map
@modelcontextprotocol/server-pdf
@modelcontextprotocol/server-scenario-modeler
@modelcontextprotocol/server-shadertoy
@modelcontextprotocol/server-sheet-music
@modelcontextprotocol/server-system-monitor
@modelcontextprotocol/server-threejs
@modelcontextprotocol/server-transcript
@modelcontextprotocol/server-video-resource
@modelcontextprotocol/server-wiki-explorer
commit: |
antonpk1
approved these changes
Mar 10, 2026
ochafik
added a commit
that referenced
this pull request
Mar 10, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
After externalizing zod in #534, consumers on zod 3.25.x hit
keyValidator._parse is not a functionat runtime when parsing schemas that compose with SDK types.Root cause
src/generated/schema.tsimports{ z }from"zod"and then composes with schemas from@modelcontextprotocol/sdk/types.js:import { z } from "zod"returns the v3 APIimport * as z from 'zod/v4'→ always v4 APIWhen a v3-created wrapper (
z.array,z.object,z.record) parses a v4 schema instance, it tries to call the v3 internal._parse()/._parseSync()— which zod v4 removed. Result:TypeError: keyValidator._parse is not a function.This was masked before #534 because zod was bundled — all schemas shared one inlined zod copy. Externalizing exposed the mismatch on zod-3.x consumers (e.g. anthropics/apps#27234).
Fix
Import from
"zod/v4"in generated schemas. This subpath is exported by both zod 3.25+ and zod 4.x, so the existingpeerDependencies.zod: "^3.25.0 || ^4.0.0"range is preserved."zod"import"zod/v4"importTesting
npm test— 121 passnpx tsc --noEmit— typecheck clean (includingschema.test.tsz.inferround-trip)npm run build:all— all examples build (via pre-commit hook)https://claude.ai/code/session_013xQUegrvVGct5xpqeSL5av