Java 弹簧靴不';t对ZoneDateTime使用自定义反序列化程序

Java 弹簧靴不';t对ZoneDateTime使用自定义反序列化程序,java,spring,spring-boot,jackson,deserialization,Java,Spring,Spring Boot,Jackson,Deserialization,我正在尝试设置spring引导配置,以使用自定义的序列化程序和反序列化程序。 反序列化程序代码 public class CustomZonedDateTimeDeserializer extends JsonDeserializer<ZonedDateTime> { @Override public ZonedDateTime deserialize(JsonParser jsonParser, DeserializationContext context)

我正在尝试设置spring引导配置,以使用自定义的序列化程序和反序列化程序。

反序列化程序代码

public class CustomZonedDateTimeDeserializer extends JsonDeserializer<ZonedDateTime> {

    @Override
    public ZonedDateTime deserialize(JsonParser jsonParser, DeserializationContext context)
            throws IOException, JsonProcessingException {
        ObjectCodec oc = jsonParser.getCodec();
        TextNode node = (TextNode) oc.readTree(jsonParser);
        String dateString = node.textValue();
        return ZonedDateTime.parse(dateString, CustomZonedDateTimeSerializer.formatter);
    }

@Override
public Class<?> handledType() {
    return ZonedDateTime.class;
}
public class CustomZonedDateTimeSerializer extends JsonSerializer<ZonedDateTime> {

    @Override
    public Class<ZonedDateTime> handledType() {
        return ZonedDateTime.class;
    }

    public final static DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZ");

    @Override
    public void serialize(ZonedDateTime date, JsonGenerator generator, SerializerProvider provider)
            throws IOException, JsonProcessingException {
        final String dateString = date.format(formatter);
        generator.writeString(dateString);

    }

}
我正在创建一个REST API,所以我的控制器中有一个:

@Configuration
public class JacksonConfiguration {

    @Autowired
    Jackson2ObjectMapperBuilder jacksonBuilder;

    @PostConstruct
    public void configureJackson() {

        final CustomZonedDateTimeSerializer serializer = new CustomZonedDateTimeSerializer();
        jacksonBuilder.serializers(serializer);

        final CustomZonedDateTimeDeserializer deserializer = new CustomZonedDateTimeDeserializer();
        jacksonBuilder.deserializers(deserializer);
    }

}
@RequestMapping(value = "date", method = { RequestMethod.GET })
@ApiOperation(value = "", notes = "")
public ResponseWrapper<String> testDATE(
        @RequestParam @ApiParam(value = "", required = true) ZonedDateTime date) {
    System.out.println(date.toString());
    return new ResponseWrapper<String>(date.toString());
}
@RequestMapping(value=“date”,method={RequestMethod.GET})
@ApiOperation(值=”,注释=”)
公共响应包装测试日期(
@RequestParam@ApiParam(value=”“,required=true)ZonedDateTime(日期){
System.out.println(date.toString());
返回新的ResponseWrapper(date.toString());
}
到目前为止,我已经尝试过: 创建一个自定义模块,并将其作为@Bean添加到配置中,将序列化程序和反序列化程序添加到配置中的jackonBuilder对象中,以及类似本文中的代码

我是错过了什么还是做错了什么? 每次尝试时都会出现以下错误:

无法将“java.lang.String”类型的值转换为所需类型 “java.time.ZoneDateTime”;嵌套异常为 org.springframework.core.convert.ConversionFailedException:未能 从类型[java.lang.String]转换为类型 [@org.springframework.web.bind.annotation.RequestParam @io.swagger.annotations.ApiParam java.time.ZonedDateTime]作为值 “2018-07-10T00:00:00+0000”;嵌套异常为 java.lang.IllegalArgumentException:解析值的尝试失败 [2018-07-10T00:00:00+0000]


我每次都发送以下值:2018-07-10T00:00:00+0000,并且该值甚至没有到达我的断点所在的反序列化程序。

在配置类中添加此bean:

@Bean
public Jackson2ObjectMapperBuilder configureObjectMapper() {
    Jackson2ObjectMapperBuilder builder = new Jackson2ObjectMapperBuilder();
    final CustomZonedDateTimeSerializer serializer = new CustomZonedDateTimeSerializer();
    builder.serializers(serializer);

    final CustomZonedDateTimeDeserializer deserializer = new CustomZonedDateTimeDeserializer();
    builder.deserializers(deserializer);
    return builder;
}

似乎我无法在GET请求中发送ZoneDateTime。当我切换到POST后,Spring能够自动解析日期

我只添加了spring.jackson.deserialization.adjust\u dates\u to\u context\u time\u zone=true,因此它考虑了时区


如果有人想在GET中发送它,他必须发送一个字符串并解析它,而不是将ZonedDateTime定义为参数

您必须为
Jackson2ObjectMapperBuilder
提供工厂方法。我认为这里发生的事情是,当您的@PostConstruct被执行时,ObjectMapper已经被装箱了——但这只是一个假设。您是否尝试过使用
org.springframework.core.convert.converter
来代替?我发现反序列化要简单得多。Spring-boot应该自动注册序列化程序和反序列化程序类。确保它们位于自动扫描包层次结构中。删除JacksonConfiguration类-将为您配置spring提供的可注入ObjectMapper。这会起作用(我以前尝试过),但我的问题是我使用了错误的http方法