記一次JVM時區引發的問題

問題描述:
有個業務需求,統計某個時間點之前數據庫中的數據,不傳時間的話就統計所有,接口寫完之後做了兩個測試,分別是不傳時間和傳當天晚上23:00的時間,當天晚上23:00屬於未來時間,兩次統計的記錄數應該是一樣的纔對,可事實是兩者不一致。

傳23:00的時間的統計數據每次統計的結果是一樣的,比不傳時間統計的數據要少,不傳時間每次統計的數據都是不一樣的,因爲數據庫的數據一直在變,所以23:00的時間統計的一直是某個歷史時間的數據,因爲統計結果每次都一樣,當時下意識看了下時間,是17點多,而公司的業務除了國內還有美國,數據時不時的有時區問題,第一直覺是時區問題,就以15:00作爲參數,直接用sql統計了一下數據庫的數據,果然跟通過postman傳23:00的統計結果是一致的。

如果是時區問題,那到底是哪裏出問題了呢?本機是Shanghai,服務器上通過date -R查看也是東八區,Java不應該默認使用的本機時區嗎?打開MySQL的日誌收集,查看sql,雖然postman傳的23:00,數據庫日誌打印的確實是15:00。

解決方案:
問題確實是時區問題,jvm默認確實是使用的本機時區設置,但,不是通過date -R查看。JVM默認獲取的Centos和Ubuntu的時區是文件/etc/localtime的時區。通過以下命令查看:

#ls -l /etc/localtime
lrwxrwxrwx 1 root root 27 Dec 2 18:53 /etc/localtime -> /usr/share/zoneinfo/Etc/UTC

結果發現果然時區不一致,服務器是以原子鐘爲基礎的統一時間,跟運維溝通後,發現拉取的基礎鏡像有問題,換了一個docker鏡像就可以了。

但是我們也可以通過以下方式自己設置時區:
CentOS6、Ubuntu16:

# cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime

CentOS7、RHEL7:

# timedatectl list-timezones |grep Shanghai    #查找時區
Asia/Shanghai
# timedatectl set-timezone Asia/Shanghai    #設置時區

或者手動建立軟連接

# ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章