@JsonFormat 反序列化失败
@JsonFormat deserialization fails
我有一个 class,只有一个字段:
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSZ", timezone = "PST")
@JsonProperty("myDate")
private Date myDate;
当我尝试将 json 字符串反序列化为对象时:
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.setTimeZone(TimeZone.getTimeZone("PST"));
ObjectNode node = objectMapper.createObjectNode();
node.put("myDate", "2016-11-06");
Object pojo = objectMapper.treeToValue(node, SomeClass.class);
失败并出现以下异常:
com.fasterxml.jackson.databind.JsonMappingException: Failed to parse Date value '2016-11-06' (format: "yyyy-MM-dd'T'HH:mm:ss.SSSZ"): Unparseable date: "2016-11-06"
.
.
.
Caused by: java.lang.IllegalArgumentException: Failed to parse Date value '2016-11-06' (format: "yyyy-MM-dd'T'HH:mm:ss.SSSZ"): Unparseable date: "2016-11-06"
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateBasedDeserializer._parseDate(DateDeserializers.java:158)
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:261)
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:245)
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:490)
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:95)
at com.fasterxml.jackson.databind.deser.BeanDeserializer.vanillaDeserialize(BeanDeserializer.java:260)
注释@JsonFormat 不应该只适用于序列化吗?至少这是我通过阅读此常见问题解答所理解的内容:http://wiki.fasterxml.com/JacksonFAQDateHandling。在这里,我无法将 json 字符串反序列化为对象。
甚至 JsonFormat java 文档也没有谈论它在反序列化过程中的使用:http://fasterxml.github.io/jackson-annotations/javadoc/2.0.0/com/fasterxml/jackson/annotation/JsonFormat.html
我是不是理解错了这个功能,还是我的代码做错了什么?
不,@JsonFormat 注释适用于序列化和反序列化。因此,在反序列化中,它用于使用 DateFormat.parse 方法将日期时间字符串解析为日期时间对象,在序列化中,使用 DateFormat.format 方法将日期时间对象格式化为日期时间字符串。
有关详细信息,请查看 DateSerializer 和 DateDeserializers 类。
如果值是 UTC 时间,您应该只使用 'Z'。因此,在您的情况下,将日期时间格式更改为 "yyyy-MM-dd'T'HH:mm:ss.SSS" 并将日期时间值传递为“2016-11-06T05:00:35.657”。这将成功解析。
我有一个 class,只有一个字段:
@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSZ", timezone = "PST")
@JsonProperty("myDate")
private Date myDate;
当我尝试将 json 字符串反序列化为对象时:
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.setTimeZone(TimeZone.getTimeZone("PST"));
ObjectNode node = objectMapper.createObjectNode();
node.put("myDate", "2016-11-06");
Object pojo = objectMapper.treeToValue(node, SomeClass.class);
失败并出现以下异常:
com.fasterxml.jackson.databind.JsonMappingException: Failed to parse Date value '2016-11-06' (format: "yyyy-MM-dd'T'HH:mm:ss.SSSZ"): Unparseable date: "2016-11-06"
.
.
.
Caused by: java.lang.IllegalArgumentException: Failed to parse Date value '2016-11-06' (format: "yyyy-MM-dd'T'HH:mm:ss.SSSZ"): Unparseable date: "2016-11-06"
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateBasedDeserializer._parseDate(DateDeserializers.java:158)
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:261)
at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:245)
at com.fasterxml.jackson.databind.deser.SettableBeanProperty.deserialize(SettableBeanProperty.java:490)
at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:95)
at com.fasterxml.jackson.databind.deser.BeanDeserializer.vanillaDeserialize(BeanDeserializer.java:260)
注释@JsonFormat 不应该只适用于序列化吗?至少这是我通过阅读此常见问题解答所理解的内容:http://wiki.fasterxml.com/JacksonFAQDateHandling。在这里,我无法将 json 字符串反序列化为对象。
甚至 JsonFormat java 文档也没有谈论它在反序列化过程中的使用:http://fasterxml.github.io/jackson-annotations/javadoc/2.0.0/com/fasterxml/jackson/annotation/JsonFormat.html
我是不是理解错了这个功能,还是我的代码做错了什么?
不,@JsonFormat 注释适用于序列化和反序列化。因此,在反序列化中,它用于使用 DateFormat.parse 方法将日期时间字符串解析为日期时间对象,在序列化中,使用 DateFormat.format 方法将日期时间对象格式化为日期时间字符串。
有关详细信息,请查看 DateSerializer 和 DateDeserializers 类。
如果值是 UTC 时间,您应该只使用 'Z'。因此,在您的情况下,将日期时间格式更改为 "yyyy-MM-dd'T'HH:mm:ss.SSS" 并将日期时间值传递为“2016-11-06T05:00:35.657”。这将成功解析。