feat: support zod 4 and zod-to-openapi v8#22
Merged
Merged
Conversation
BREAKING CHANGE: peer dependency on zod is now ^4. Drop zod 3 support. - Bump peer `zod` to ^4 and dep `@asteasolutions/zod-to-openapi` to ^8.5.0 - Replace `z.SafeParseReturnType` with `z.ZodSafeParseResult` (renamed in zod 4) - Validated middleware now casts to `z.output<T>` so `req.params/body/query` infer correctly under zod 4's stricter input/output split - Replace removed `ZodEffects` ref-resolution branch with `getRefId()` from zod-to-openapi v8 — pipes/transforms on registered schemas still resolve back to their `$ref` - Update test assertions for zod 4's new "Invalid input: expected X, received Y" default error format - Pin packageManager to yarn@1.22.22 to match the existing v1 lockfile Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Three follow-up fixes after the initial zod 4 bump: - Replace `TBody extends ZodTypeAny` (which collapses to `unknown` under zod 4's stricter variance) with bare `TBody`/`TQuery`/etc. generics and a conditional `InferOutput<T>` helper that reads `T["_zod"]["output"]`. This restores proper inference for `req.body`, `req.query`, and `req.params` inside `openAPIRoute(...)` handlers. - `InferOutput<T>` falls back to `any` when no schema is declared, matching the previous behavior so routes without explicit schemas don't suddenly break. - Re-export `extendZodWithOpenApi` and `ZodOpenAPIMetadata` from the package root so the `.openapi()` augmentation is more discoverable for consumers; under `module: "nodenext"` callers may still need to import `@asteasolutions/zod-to-openapi` themselves to fully activate it. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
|
this looks good to me, i'll let @bengotow weigh in as well. |
bengotow
approved these changes
May 26, 2026
|
🎉 This PR is included in version 7.0.0 🎉 The release is available on: Your semantic-release bot 📦🚀 |
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.
Summary
zodto^4(breaking) and@asteasolutions/zod-to-openapito^8.5.0ZodEffects,SafeParseReturnType)req.params/body/queryinfer correctly under zod 4's stricter input/output split — without this, every downstreamopenAPIRoute(...)handler loses its inferred request types_def.openapi._internal.refIdintrospection with the publicgetRefId()helper from zod-to-openapi v8packageManagertoyarn@1.22.22to match the existing v1 lockfile (corepack now auto-selects the right yarn)