chore: upgrade springdoc-openapi to 3.1.0 for Spring Data 4 compatibility - #2112
Conversation
…lity springdoc-openapi 2.8.13's QuerydslPredicateOperationCustomizer class (part of springdoc-openapi-starter-webmvc-ui's transitive springdoc-openapi-starter-common) was compiled against spring-data-commons < 4.0, where TypeInformation lived in org.springframework.data.util. This project resolves spring-data-commons 4.0.6 (matching Spring Boot 4.0.7), where TypeInformation moved to org.springframework.data.core - a package that no longer exists from that customizer's point of view. Regular application startup never reflectively introspects that customizer's method signatures, so the incompatibility stays invisible in normal operation. It does surface under Spring's AOT processing (tried while investigating why processTestAot/processAot weren't wired up, since org.springframework.boot.aot must be applied separately from org.springframework.boot): PersistenceAnnotationBeanPostProcessor's more aggressive bean introspection during AOT context refresh walks that class and throws NoClassDefFoundError for the no-longer-existent org.springframework.data.util.TypeInformation. springdoc-openapi 3.1.0 (targeting the Spring Boot 4.1 line, still binary-compatible here per this project's own Spring Boot BOM/dependency management) ships that same customizer recompiled against the moved TypeInformation. Verified the application's own springdoc usage (GroupedOpenApi, OpenApiCustomizer, OperationCustomizer in DocumentationConfig) is unchanged in 3.1.0's bytecode - no source changes needed - and confirmed the fix: compiles clean, full test suite green (1061/1061), and processTestAot no longer fails on TypeInformation (a separate, unrelated Spring Data AOT class-generation limitation remains, tracked separately - AOT itself is not yet usable here). Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
Updates the server’s OpenAPI/Swagger integration dependency to resolve a Spring Data 4 compatibility issue during Spring AOT processing (caused by a moved TypeInformation type).
Changes:
- Bump
springdoc-openapi(via version catalog) from2.8.13to3.1.0.
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
|
btw. this dependency bump is necessary to support Spring Boot JPA AOT processing as the currently used version is not fully compatible with Spring Boot 4. |
|
Note: our script uses Toolbox w/ |
|
That dep update was missed when we did the spring boot 4 upgrade. In general checking minor version updates is fine, maybe we can add a flag to the script to also check if there are major updates available which anyway have to be manually vetted. |
Upgrading springdoc to 3.1.0 (#2112) also changed the spec version it emits: springdoc 3.x defaults springdoc.api-docs.version to OPENAPI_3_1, where 2.8.13 defaulted to OPENAPI_3_0. That was a side effect of the bump rather than a decision, and it silently dropped a field from the document. new Schema<>().type("integer") sets only the legacy string `type` and leaves the 3.1 `types` set null, and a 3.1 document does not serialize the former. The four rate limit headers have therefore been documented with no type at all since the upgrade. Building them through IntegerSchema populates both fields, so they keep a type whichever version springdoc emits. The dev configuration pins api-docs back to 3.0. Beyond restoring the document as it was, it silences a warning that OpenAPI 3.1 draws out of swagger-core 2.2.52 on every schema springdoc clones: SpringDocUtils : Json Processing Exception occurred: Cannot construct instance of `java.util.HashSet` [...] from String value ('integer') (through reference chain: io.swagger.v3.oas.models.media.JsonSchema["type"]) Its 3.1 mapper writes a single type as a bare string but only reads an array back, so cloneViaJson cannot re-read what it just wrote. It logs and falls back to the original object, so the document still renders. A schema with two types serializes as an array and round-trips fine, which is why only some schemas trip it. Nothing in this repository can fix that asymmetry; only avoiding 3.1 avoids it. Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Why
springdoc-openapi2.8.13'sQuerydslPredicateOperationCustomizer(pulled in transitively viaspringdoc-openapi-starter-webmvc-ui→springdoc-openapi-starter-common) was compiled against aspring-data-commonsversion older than 4.0, whereTypeInformationlived inorg.springframework.data.util. This project resolvesspring-data-commons:4.0.6(matching Spring Boot 4.0.7), whereTypeInformationmoved toorg.springframework.data.core— a package that class no longer knows about.Regular application startup never reflectively introspects that customizer's method signatures, so the incompatibility is invisible in normal operation. It surfaces under Spring's AOT processing:
PersistenceAnnotationBeanPostProcessor's more aggressive bean introspection during AOT context refresh walks the class and throwsNoClassDefFoundErrorfor the now-nonexistentorg.springframework.data.util.TypeInformation. (Found while investigating whyprocessAot/processTestAotweren't even registered in this build — turned outorg.springframework.boot.aotmust be applied as a separate plugin fromorg.springframework.boot, which is a separate finding not included in this PR.)What
Bumps
springdocto3.1.0, which ships that same customizer recompiled against the movedTypeInformation. Verified via bytecode inspection against the published jars (not just changelog reading) that:org.springframework.data.core.TypeInformation.GroupedOpenApi,OpenApiCustomizer,OperationCustomizerinDocumentationConfig) is unchanged in 3.1.0's bytecode — no source changes needed.Verification
DocumentationConfigTestpasses.processTestAot(with the AOT plugin applied locally, not part of this PR) — theTypeInformationfailure is gone. A separate, unrelated Spring Data AOT class-generation limitation remains when processing many@SpringBootTestclasses that share a context configuration, so AOT itself isn't usable here yet regardless of this fix — but that's no longer blocked on this specific incompatibility.Note:
springdoc-openapi3.1.0 targets the Spring Boot 4.1 line's BOM; this project pins Spring Boot 4.0.7. This is a minor-version gap that Spring Boot's own dependency management should reconcile transitively (confirmed by the green full suite), same as any other dependency slightly ahead of the pinned Boot BOM.🤖 Generated with Claude Code