我有Java 8 Spring网络应用程序,它将支持多个区域.我需要为客户位置制作日历活动.因此,假设我的网站和Postgres服务器托管在MST时区(但我想如果我们去云端,它可能就在任何地方).但客户是在美国东部时间.所以,按照我读到的一些最佳实践,我想我会以UTC格式存储所有日期时间.数据库中的所有日期时间字段都声明为TIMESTAMP.
所以这是我如何采用LocalDateTime并转换为UTC:
ZonedDateTime startZonedDT = ZonedDateTime.ofLocal(dto.getStartDateTime(), ZoneOffset.UTC, null);
//appointment startDateTime is a LocalDateTime
appointment.setStartDateTime( startZonedDT.toLocalDateTime() );
Run Code Online (Sandbox Code Playgroud)
现在,例如,当搜索日期时,我必须从请求的日期时间转换为UTC,获取结果并转换为用户时区(存储在数据库中):
ZoneId userTimeZone = ZoneId.of(timeZone.getID());
ZonedDateTime startZonedDT = ZonedDateTime.ofLocal(appointment.getStartDateTime(), userTimeZone, null);
dto.setStartDateTime( startZonedDT.toLocalDateTime() );
Run Code Online (Sandbox Code Playgroud)
现在,我不确定这是正确的方法.我也想知道如果因为我从LocalDateTime到ZonedDateTime,反之亦然,我可能会失去任何时区信息.
这是我所看到的,这对我来说似乎不正确.当我从UI收到LocalDateTime时,我得到了这个:
2016-04-04T08:00
Run Code Online (Sandbox Code Playgroud)
ZonedDateTime =
dateTime=2016-04-04T08:00
offset="Z"
zone="Z"
Run Code Online (Sandbox Code Playgroud)
然后,当我将转换后的值分配给我的约会LocalDateTime时,我存储:
2016-04-04T08:00
Run Code Online (Sandbox Code Playgroud)
我觉得因为我存储在LocalDateTime中我失去了转换为ZonedDateTime的时区.
我应该让我的实体(约会)使用ZonedDateTime而不是LocalDateTime,以便Postgres不会丢失该信息吗?
---------------- 编辑 ----------------
在Basils出色的答案之后,我意识到我很不喜欢用户时区 - 所有约会都是针对特定位置的,因此我可以将所有日期时间存储为UTC,然后在检索时将它们转换为位置时区.我提出了以下后续问题