IT俱乐部 Java JVM默认时区为:Asia/Shanghai与java程序中GMT+08不一致异常

JVM默认时区为:Asia/Shanghai与java程序中GMT+08不一致异常

在Spring程序中配置了spring.jackson.time-zone=GMT+08时,部分时间相差一个小时问题,且是固定的时间出现了固定的时差问题。

经过排查,发现是JVM的默认时区为

Asia/Shanghai,两者不一致,然后Asia/Shanghai 这个时区并不一定与GMT+08这个时区相等,他们是2种定义标准。

Asia/Shanghai 这个代表的是中国的时区,但在历史中,有国家(包含中国)政策颁布了在1986-1991年等还存在夏令时。

在这样的时间区间,夏季时,会将时间拨快1个小时(即东9区时间),夏季结束时会再次将时间拨回一个小时(即东8区时间)。

所以要保证程序显示的时间没有问题,需要将JVM和spring.jackson.time-zone设置的时区保持一致即可解决问题

JVM中设置为

Asia/Shanghai,经代码调试出现的底层时区调整的测试案例。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
import java.text.SimpleDateFormat;
import java.util.Date;
 
/**
 * @author Ashen
 * @date 16/07/2019
 */
public class Test {
 
    public static SimpleDateFormat sdf = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss");
 
    static int[] offsets = {
            28800000,
            29143000,
            32400000,
            3600000
    };
    public static void main(String[] args) {
        test2();
    }
 
    public static void test1(){
        Date date0 = new Date(1986 - 1900, 07 - 1, 29);
        Date date1 = new Date(1980 - 1900, 07 - 1, 29);
        Date date2 = new Date(1988 - 1900, 07 - 1, 29);
    }
 
    public static void test2() {
        // 以下为JVM中时区为:Asia/Shanghai时的偏移量参数值(共9对,分别为9年夏令时的开启与结束点)
        long transitions[] = {
                -9048018124799999L,
                -8918966038528000L,
                -3823593062399950L,
                -3781140480000000L,
                -3722379263999950L,
                -3651969024000000L,
                2111569920000050L,
                2158623129600000L,
                2232955699200050L,
                2287440691200000L,
                2361773260800050L,
                2416258252800000L,
                2493068083200050L,
                2547553075200000L,
                2621885644800050L,
                2676370636800000L,
                2750703206400050L,
                2805188198400000L,
                8660385792000000L
        };
        for(int i=0;i> 12;
            Long field2 = transitions[i] > 60;
            Long field3 = transitions[i] > 60;
            Long field4 = transitions[i] > 60;
            Date date = new Date(longTime);
            System.out.println("时间"+getIndexStr(i)+": "+sdf.format(date)+" 保留值>>"+field2+" 日光节约量 >> "+getOffset(field3)+" GMT偏移量 >> "+getOffset(field4));
        }
 
    }
 
    public static String getIndexStr(int i){
        if(i

下面为运行结果:清晰的看到Asia/Shanghai 时区的调整时间点与调整量。

transitions[] 中的值来源于DEBUG程序时复制jvm中的数据。

以上为个人经验,希望能给大家一个参考,也希望大家多多支持IT俱乐部。

本文收集自网络,不代表IT俱乐部立场,转载请注明出处。https://www.2it.club/code/java/6040.html
上一篇
下一篇
联系我们

联系我们

在线咨询: QQ交谈

邮箱: 1120393934@qq.com

工作时间:周一至周五,9:00-17:30,节假日休息

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

返回顶部