发现 JSTL 时区 (KST) 实现错误

JSTL timezone (KST) implementation error found

在练习 JSTL timeZone 标签时,我尝试了 运行 这两个动作:

<c:set var="now" value="<%= new java.util.Date() %>" />
<fmt:timeZone value="GMT+9:00">
    <fmt:formatDate value="${now}" type="both"
                    dateStyle="full" timeStyle="full"/>
</fmt:timeZone>
<%-- and --%>
<fmt:timeZone value="KST">
    <fmt:formatDate value="${now}" type="both"
                    dateStyle="full" timeStyle="full"/>
</fmt:timeZone>

我相信他们应该产生相同的结果。但是,它们会产生以下两个不同的时间值。

2017 年 8 月 15 日星期二晚上 8:03:27 GMT+09:00

格林威治标准时间 2017 年 8 月 15 日星期二上午 11:03:27

我是不是漏掉了什么或者实现不正确? 如果执行不当,我应该联系谁?

不建议使用三字母时区 ID。它们已被弃用。并非所有这些都受支持。

oracle java docs

Three-letter time zone IDs

For compatibility with JDK 1.1.x, some other three-letter time zone IDs (such as "PST", "CTT", "AST") are also supported. However, their use is deprecated because the same abbreviation is often used for multiple time zones (for example, "CST" could be U.S. "Central Standard Time" and "China Standard Time"), and the Java platform can then only recognize one of them.

GMT+09:00 不是时区,它是 UTC offset: a difference (in hours, minutes and seconds) from UTC. It just means "9 hours ahead of UTC", and it's not attached to any specific region or country. (most systems, though, usually treats the offset as a "special type" of timezone, just to ).

KST 是一个 abbreviation for Korea Standard Time, but is not a "true" timezone. Timezones names are not really standardized, but many systems use IANA timezones names(始终采用 Region/City 格式,如 Asia/SeoulEurope/London)。 系统通常避免使用短缩写(如 CSTKST),因为它们是 ambiguous and not standard.

今天的时区 Asia/Seoul 使用 KST 缩写,但这在过去也被 Asia/Pyongyang 使用。虽然,它们不是同一个区域。

时区是一个地区在其历史期间曾经、曾经和将要拥有的所有不同时差的集合。今天 Asia/Seoul 使用 +09:00 偏移量,但 Asia/Pyongyang 过去也使用过,因此它们的历史数据不同(这就是为什么它们是不同的区域)。

平壤有+08:30 offset until 1912,后来改为+09:00。但在 2015 年它再次更改为 +08:30 并一直使用到今天。

首尔有一个 different offset history:过去(50 年代)也使用 +08:30,夏令时(夏季改为 +09:30),然后在 1961 年它更改为 +09:00,有一段时间有夏令时,今天只使用 +09:00,没有夏令时。

所有这些变化都是由政府和法律定义的,系统无法控制。仅仅因为一个时区(一个地区)今天使用了一些偏移量,不能保证它会永远使用它。 所以,虽然 KST 今天可以成为 +09:00 的 "synonym",但这并不意味着它会永远这样。


因此,当您使用 GMT+09:00 时,您只使用偏移量,与特定时区没有任何关联(因为 there are lots of timezones that can use this offset)。

在第二种情况下,日期似乎正在从 KST(偏移量 +09:00)转换为 UTC(偏移量零,或 "GMT")。请注意,第一种情况是偏移量 +09:00 中的晚上 8 点,第二种情况是 UTC 中的上午 11 点(偏移量为零,或 "GMT"),这是正确的。

也许 JSTL 无法识别 KST(因为它的歧义)并使用 UTC 作为默认值。我会尝试用 Asia/Seoul 替换它,看看会发生什么。