Affects: 6.0.0.M5 (but also 5.x)


I'm trying to get an immutable representation of the query parameters in my @RestController, like this:

@RestController
public class MyController {

    @RequestMapping("/foo")
    public void foo(A a) {
    }

    record A(String s, B b) {
    }

    record B(Integer i) {
    }
}

For single-level query params this works as expected: GET /foo?s=xyz

But as soon as I try to set b.i using GET /foo?b.i=42 it will throw an exception, because AbstractNestablePropertyAccessor is looking for a default constructor:

java.lang.NoSuchMethodException: com.example.demo.MyController$B.<init>()
    at java.base/java.lang.Class.getConstructor0(Class.java:3585) ~[na:na]
    at java.base/java.lang.Class.getDeclaredConstructor(Class.java:2754) ~[na:na]
    at org.springframework.beans.AbstractNestablePropertyAccessor.newValue(AbstractNestablePropertyAccessor.java:910) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractNestablePropertyAccessor.createDefaultPropertyValue(AbstractNestablePropertyAccessor.java:883) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractNestablePropertyAccessor.setDefaultValue(AbstractNestablePropertyAccessor.java:870) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractNestablePropertyAccessor.getNestedPropertyAccessor(AbstractNestablePropertyAccessor.java:842) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractNestablePropertyAccessor.getPropertyAccessorForPropertyPath(AbstractNestablePropertyAccessor.java:816) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractNestablePropertyAccessor.setPropertyValue(AbstractNestablePropertyAccessor.java:257) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.beans.AbstractPropertyAccessor.setPropertyValues(AbstractPropertyAccessor.java:104) ~[spring-beans-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.validation.DataBinder.applyPropertyValues(DataBinder.java:889) ~[spring-context-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.validation.DataBinder.doBind(DataBinder.java:780) ~[spring-context-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.web.bind.WebDataBinder.doBind(WebDataBinder.java:207) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
    at org.springframework.web.bind.ServletRequestDataBinder.bind(ServletRequestDataBinder.java:129) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]

Thanks for your help!

Comment From: rstoyanchev

@jhoeller this looks like it should be covered/superseded by #20806? Maybe just an extra comment there to ensure it works for records too.

Comment From: rstoyanchev

This is covered by #20806.