简体   繁体   中英

Spring Rest - bind nested DTO object to @RequestParams

I want to bind get params to my DTO. My problem is mapping the nested list my DTO has.

controller class:

@PostMapping(value = "test-endpoint")
public ResponseEntity<String> doStuff(@Valid @RequestParams MyDto myDto) {
    // do stuff
}

parent DTO:

public class MyDto {
    @NotNull
    private String fieldA;

    @Valid
    @NotNull
    private List<MyNestedDto> nestedDto;
}

Nested DTO:

public class MyNestedDto {
    @NotNull
    private String nestedFieldA;

    @NotNull
    private String nestedFieldB;

    // more fields
}

I have a service that sends a POST request to my controller. The request cannot be changed hence why I can't use @RequestBody annotation.

The request looks like that:

http://localhost:8080/api/test-endpoint?nestedDto={"more":[{"nestedFieldA":"example","nestedFieldB":"example"}]}&fieldA=123

Is there a way to bind the nested list to get params?

Edit *

Registering a converter doesn't seem to work, my converter convert method is not even called.

@Configuration
public class WebConfiguration implements WebMvcConfigurer {
    @Override
    public void addFormatters(FormatterRegistry registry) {
        registry.addConverter(new MyConverter());
    }
}

public class MyConverter implements Converter<String, MyDto> {

    @Override
    public MyDto convert(String source) {
        // it never reaches there
        ObjectMapper objectMapper = new ObjectMapper();
        
        return null; // return null for testing purposes
    }
}
public class AController {
     private final ObjectMapper objectMapper;
     private final Validator validator;

     public AController(ObjectMapper objectMapper,Validator validator){
          this.objectMapper = objectMapper;
          this.validator = validator;
     }

     @PostMapping(value = "test-endpoint")
     public ResponseEntity<String> doStuff(@RequestParam("nestedDto") String nestedDto) {
           MyDto myDto = objectMapper.readValue(nestedDto);
           Set<ConstraintViolation<MyDto>> constraintViolation = 
           validator.validate(myDto);
           if (!constraintViolation.isEmpty()) {
                throw new ConstraintViolationException(constraintViolation);
           }
     }

}

This is pseudo code so i just write it to demonstrate how to solve the problem. If you want more elegant way, you have to change request because request is wrong here.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM