首页 > 解决方案 > Java Jsonb在ISO8601中反序列化UTC日期时间

问题描述

我正在使用 JSON-B(yasson 实现)并且我正在接收具有这样一个字段的对象的数据

{
  ...
  "timestamp": "2020-03-19T06:42:42Z",
  ...
}

对于 UTC 日期时间值,这是完全标准的 ISO 8601。现在对应的 Java 类只声明了一个 Date 成员变量,没有其他特定的注解

...
 private Date timestamp;
...

一切似乎工作正常,看起来 JSON-B 实现正确理解为 UTC,而无需我使用@JsonbDateFormat注释指定格式。我想我很确定,因为我检查过

ZonedDateTime datetimeCheck = ZonedDateTime.of(2020, 3, 19, 6, 42, 42, 0, ZoneId.of("UTC"));
Date parsedDateFromJson = myModel.getTimestamp();
boolean compareTs = parsedDateFromJson.equals(Date.from(datetimeCheck.toInstant()));

但是,当我运行另一个测试从日期时间值中删除“Z”时,它会产生正确的结果,我希望它会产生一个不同的结果,将日期时间值解释为本地而不是 UTC。令我大吃一惊的是,JSON-B 得到的 Date 对象是完全一样的。我在这里想念什么?为什么2020-03-19T06:42:42Z2020-03-19T06:42:42是同一件事?(我不认为他们是)。或者,当没有指定时区时,JSON-B 实现是否总是将 UTC 视为默认值?

谢谢

标签: javajsondatetimejsonb-apiyasson

解决方案


或者,当没有指定时区时,JSON-B 实现是否总是将 UTC 视为默认值?

正是这个。与其名称所暗示的相反,ajava.util.Date实际上并不代表日期,而是代表时间的瞬间。具体来说,它表示自 UNIX 纪元(1970 年 1 月 1 日,格林威治标准时间 00:00:00)以来的毫秒数。

2020-03-19T06:42:42是没有区域或偏移信息的日期 + 时间。当将此日期 + 时间反序列化为 a 时java.util.Date,即一个瞬间,您需要决定如何解释日期 + 时间。这是UTC的日期+时间吗?这是您当地时区的日期+时间吗?

幸运的是,JSON-B 规范包含以下内容:“如果本节未另行指定,则使用 GMT 标准时区和从 UTC 格林威治指定的偏移量。” 正如此声明所示,作者选择将没有时区的日期 + 时间解释为 UTC 的日期 + 时间。


推荐阅读