我尝试使用Jackson读取JSON文件并将其中一个字段存储为epoch毫秒作为Java Instant
,但是反序列化的行为不符合预期。
以下是我在尝试阅读时间戳时所看到的内容:
1503115200000
杰克逊正在将Instant
字段设为+49601-10-28T16:00:00Z
。
这似乎是因为杰克逊的默认设置是使用Instant.ofEpochSecond(Long l)
而不是Instant.ofEpochMilli(Long l)
来读取时间戳。
有没有办法让杰克逊ObjectMapper
使用ofEpochMilli
方法代替?这就是我目前对ObjectMapper
:
ObjectMapper om = new ObjectMapper()
.registerModule(new JavaTimeModule())
.configure(SerializationFeature.WRITE_DATE_TIMESTAMPS_AS_NANOSECONDS, false)
.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false)
.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
.setSerializationInclusion(Include.NON_NULL);
注意
如果我将输入JSON更改为ISO日期(例如2017-08-19T04:00:00Z
)或时间秒(例如1503115200
),则Instant
字段可以正确设置。
不幸的是,JSON输入必须是纪元毫秒,例如1503115200000
。
答案 0 :(得分:1)
解决方案是将.configure(DeserializationFeature.READ_DATE_TIMESTAMPS_AS_NANOSECONDS, false)
添加到ObjectMapper。完整的ObjectMapper如下所示:
ObjectMapper om = new ObjectMapper()
.registerModule(new JavaTimeModule())
.configure(SerializationFeature.WRITE_DATE_TIMESTAMPS_AS_NANOSECONDS, false)
.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false)
.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false)
.configure(DeserializationFeature.READ_DATE_TIMESTAMPS_AS_NANOSECONDS, false)
.setSerializationInclusion(Include.NON_NULL);
答案 1 :(得分:1)
如果启用了{@code READ_DATE_TIMESTAMPS_AS_NANOSECONDS}(默认情况下),则更不明确的整数类型将被读取为没有小数点的小数秒,否则它们将被读取为毫秒。
所以你需要禁用READ_DATE_TIMESTAMPS_AS_NANOSECONDS。
答案 2 :(得分:1)
对于那些使用 Spring Boot 并在其余请求反序列化期间遇到此问题的用户-在application.properties中提供此信息:
spring.jackson.deserialization.read-date-timestamps-as-nanoseconds=false
@JB Nizet的答案是正确的,但是由于Spring Boot内部具有它自己的ObjectMapper-您需要在属性中配置该值。