I'm having trouble integrating Spring with Jackson.
I have a POJO which has some Instant fields with a custom date format:
public class C{ @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "dd-MM-yyyy HH:mm:ss", timezone = "UTC") private Instant postedAtFrom; @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "dd-MM-yyyy HH:mm:ss", timezone = "UTC") private Instant postedAtTo; } Then I'm trying to use this POJO as a query parameter for a rest GET mapping:
@RestController @RequestMapping("/c") @RequiredArgsConstructor @Slf4j public class AnnounceController { @Autowired private final ObjectMapper objectMapper; @PostConstruct public void test() throws JsonProcessingException { System.out.println(objectMapper.readValue("{\"postedAtFrom\":\"20-05-2022 15:50:07\"}", C.class)); } @GetMapping public BasicResponse<Page<Announce>> get(final C filter, @NonNull final Pageable page) { return new BasicResponse<>(service.get(filter, page)); } } The PostConstruct code works fine and it prints exactly what it should print, but whenever I try to make a get to that endpoint with the very same request:
CURL GET /c?postedAtFrom=20-05-2022 15:50:07 HTTP/1.1 Host: localhost I get this exception:
org.springframework.validation.BeanPropertyBindingResult: 1 errors Field error in object 'filter' on field 'postedAtFrom': rejected value [20-05-2022 15:50:07] codes [typeMismatch.filter.postedAtFrom,typeMismatch.postedAtFrom,typeMismatch.java.time.Instant,typeMismatch] arguments [org.springframework.context.support.DefaultMessageSourceResolvable: codes [filter.postedAtFrom,postedAtFrom] arguments [] default message [postedAtFrom]] default message [Failed to convert property value of type 'java.lang.String' to required type 'java.time.Instant' for property 'postedAtFrom' nested exception is org.springframework.core.convert.ConversionFailedException: Failed to convert from type [java.lang.String] to type [@com.fasterxml.jackson.annotation.JsonFormat java.time.Instant] for value [20-05-2022 15:50:07] nested exception is java.lang.IllegalArgumentException: Parse attempt failed for value [20-05-2022 15:50:07]] Here is the code for the ObjectMapper bean:
@Bean @Primary public ObjectMapper configure(@NonNull final ObjectMapper objectMapper) { final SimpleModule javaTimeModule = new JavaTimeModule() .addDeserializer(Instant.class, InstantDeserializer.INSTANT) .addSerializer(Instant.class, InstantSerializer.INSTANCE); return objectMapper.registerModule(javaTimeModule); } I would like to to resolve this using the designed tools of Spring and Jackson. Please do not suggest a workaround like "convert it to a string" or "make a post".
Cis currently un-annotated, which means that Spring MVC will assume it's a model attribute and try to parse the query params to produce an instance. There's no JSON parsing involved at all.