如何在时区中存储和显示最初给定的日期?



我有一个服务器,它从不同时区的客户端接收数据。数据提要包含人员、他们的出生日期和其他事件的日期。出于我们的目的,如果我们能够按照给定的日期存储日期,将会很方便。

例如,如果客户端在加利福尼亚,它告诉我们该人的出生日期是5月31日,我们希望将其存储在数据库中,作为1999年5月31日,太平洋时间。这样,无论你在哪个时区,你都可以看到这个人出生于5月31日。

与此同时,我们希望能够查询这些数据,以便能够弄清楚诸如"这个人是未成年人吗"或"这件事发生在24小时之内吗?"客户端通过基于http的rest API向我们发送数据。服务器是用Java编写的(使用eclipselink)。数据库类型为postgresql。有可能满足这些要求吗?

通常,人们说要将所有内容存储为UTC,但我觉得这是一个坏主意,因为我们会丢失原始数据的时区。

UTC是可行的方法。对于timestamptz (timestamp with time zone),输入值的时区仅作为Postgres内部计算UTC的修饰符。(对于timestamp [without time zone],任何附加的时区都将被忽略!)未保存时区信息。您需要另外保存以知道在世界上发生了什么

如果您这样做,您可能还不如存储本地时间戳。只是不要搞混了。将所有内容转换为UTC(对于timestamptz自动发生),或将所有内容转换为本地时间(定义"本地":您的本地?本地到db服务器?本地用户?)。

特别是,要存储确切的时区名称(或对它的引用),而不仅仅是"pacific time"。这对于夏令时、闰秒或其他事件更准确。

详细解释:

  • 在Rails和PostgreSQL中完全忽略时区

关于时区名称和缩写:

  • 具有相同属性的时区名称在应用于时间戳
  • 时会产生不同的结果

关于时区处理:

  • 在选择计划项目时,在Postgres中考虑DST
  • 保留PostgreSQL时间戳类型的时区

Erwin Brandstetter的答案是100%正确的。

计算年龄

至于计算未成年人的年龄等问题,由于时间的关系,这有点棘手。使用Joda-Time库,您可以调用withTimeAtStartOfDay方法将DateTime对象设置为一天的第一个时刻。通常第一个时刻是00:00:00时间,但并不总是因为夏令时或其他异常。忽略"midnight"相关的类和方法,因为它们已被上述方法所取代。

此外,要真正准确地计算年龄以合法地保护自己,您可能需要将年龄计算为出生日期时间之后的一天或两个。除非您知道他们的出生时间出生的时区,否则您无法确切知道他们的年龄。

<标题>避免j.u.Date/.Calendar h1>

与java.util。日期,其他两个库中的日期-时间对象都知道它们自己分配的时区。j.u.d date特别令人困惑,因为虽然它没有分配时区,但它的toString方法应用JVM当前的默认时区,从而产生分配时区的错觉。

Joda-Time | java.time

使用java和java。时间一长,事情就清楚多了。为每个日期-时间对象指定一个时区(否则将分配JVM默认值)。您可以很容易地从一个时区转换到另一个时区。

两个库都使用不可变对象,即在原始对象的基础上创建新对象,而不是更改(变异)原始对象。

你可以调用getZone一个Joda-Time DateTime对象来获取它的时区名称(ID)和它与UTC的偏移量,如果你认为这很重要的话。

<标题> ISO 8601 h1> 解日期-时间值的可感知字符串格式的ISO 8601标准。考虑在基于文本的API中使用它们。ISO 8601现在是所有新互联网协议的标准。例如:2014-08-13T16:02:01Z2014-12-22T11:54:23+04:00 .

并使用适当的时区名称。避免使用3或4个字母的代码,因为它们既不标准化也不唯一。

相关内容

  • 没有找到相关文章

最新更新