fix: compose JAX-RS method-level @Path with class-level prefix#1007
fix: compose JAX-RS method-level @Path with class-level prefix#1007CharlesQueiroz wants to merge 1 commit into
Conversation
|
Thanks for the targeted JAX-RS fix. I have triaged it into 0.9.1-rc as the fix candidate for #1005. Review focus will be class-plus-method path composition and making sure Spring-style annotation extraction does not regress. |
|
Reviewed and verified locally — the diagnosis and fix are exactly right; same two mechanical blockers as your #1008, plus one recommendation. Verified (your branch merged onto current main, db330bf):
1. DCO (blocking): commit 2. clang-format (blocking): two lines in 3. Recommendation (would take this from good to complete): add an end-to-end Route-node test alongside the unit test — static const char *routes[] = {"/api/v1/widgets", "/api/v1/widgets/count", NULL};
ASSERT_TRUE(et_routes_exact(f, 1, routes));If you'd rather keep this PR minimal, say so and we'll add the probe-tier guard in a follow-up after merge. Known gap we're both fine deferring: With DCO + format in and CI green, this is good to merge from my side. Two solid, well-scoped fixes in a row — much appreciated. |
…ata#1005) JAX-RS splits a route across two annotations: the verb comes from a bare @GET/@POST/... and the path from a sibling @path. The annotation scan returned on the first mapping annotation, so the @get matched, defaulted the path to "/" and the sibling @path was never read. Class-level @path was never recognized as a prefix either, because a lone @path carries no verb and the scan reported no route. scan_route_annotations() now collects the whole annotation set (mapping verb + optional inline path, and a separate JAX-RS @path), then: - method-level: verb required; path = inline mapping path, else @path, else "/" - class-level prefix: inline mapping path, else @path Also recognizes bare @HEAD/@options verbs. Spring behavior is unchanged (mapping annotations keep their inline path); covered by the existing test suite plus a new regression test. Signed-off-by: Charles Queiroz <fcqueiroz@liquibase.com>
07704e1 to
041eb99
Compare
|
Applied the two blockers: sign-off added and the HEAD/OPTIONS condition in extract_defs.c is clang-format clean. Also took the recommendation rather than deferring it: added a handles_jaxrs_java probe to test_edge_types_probe.c asserting the exact Route-name set {/api/v1/widgets, /api/v1/widgets/count} through the full pipeline, guarding the class-prefix composition and the emission dedup path. Full suite passes locally. |
Fixes #1005.
Root cause
extract_route_from_annotations()returned on the first mapping annotation. For JAX-RS methods the verb and the path live in two sibling annotations:The
@GETmatched first (annotation_route_method("GET")), defaulted the path to"/", and the sibling@Pathwas never read: every method-level@Pathwas silently dropped. Class-level@Pathprefixes were never recognized either, because a lone@Pathcarries no verb, so the scan reported "no route" andspring_class_route_prefix()returned NULL.This also explains the "inconsistent" symptom in #1005: resources whose endpoints are exercised by RestAssured tests got Route nodes from the tests' full-URL string literals, masking the missing annotation-derived routes; resources without such tests showed only the class-level route.
Fix
New
scan_route_annotations()collects the whole annotation set in one pass: the mapping verb (+ optional inline path, Spring style) and a separate JAX-RS@Pathvalue. Then:extract_route_from_annotations): a verb annotation is still required (a lone@Pathsub-resource locator is not an endpoint); path = inline mapping path, else@Path, else"/".spring_class_route_prefix): inline mapping path (@RequestMapping("/api")), else class-level@Path.@HEAD/@OPTIONSverbs are now recognized alongside GET/POST/PUT/DELETE/PATCH.Spring extraction is unchanged: mapping annotations keep their inline path and the collecting scan preserves the first-mapping-annotation-wins order.
Validation
extract_java_jaxrs_path_composition_issue1005(class prefix alone, prefix + method@Path, verb preserved).@ConfigPropertyparams and generic DTO return types included) indexed with the patched binary now yields:__route__GET__/api/v1/widgets__route__GET__/api/v1/widgets/count__route__POST__/api/v1/widgets/{}/archive__route__GET__/api/v2/things/allunchanged.