如何解決java獲取時間相差8小時的問題

三種時間差錯問題:

  • java下使用new date()獲取的時間會和真實的本地時間相差8小時。
  • 本地獲取的時間沒有錯,存入數據庫的時候時間相差8小時。
  • 數據庫時間沒有錯,獲取到瞭後端,之後返回給前端相差8小時。

原因:

  • new date()調用的是jvm時間,而jvm使用的時間默認是0時區的時間,即:和北京時間將會相差8小時。
  • mybatis將本地的數據傳入到mysql數據庫服務器的時候,服務器會對數據進行檢測,會把date類型的數據自動轉換為mysql服務器所對應的時區,即0時區,所以會相差8小時。
  • springboot中對加瞭@RestController或者@Controller+@ResponseBody註解的方法的返回值默認是Json格式,
  • 所以,對date類型的數據,在返回瀏覽器端時,會被springboot默認的Jackson框架轉換,而Jackson框架默認的時區GMT(相對於中國是少瞭8小時)。所以最終返回到前端結果是相差8小時

解決方案:

手動設置jvm時間:將時間改為第8時區的時間:

TimeZone.setDefault(TimeZone.getTimeZone("GMT+8"));

溫馨提示:如果是springboot項目,可以面向切面加上這個,或者啟動main類上加上如下代碼:

@PostConstruct
    void started() {
        TimeZone.setDefault(TimeZone.getTimeZone("GMT+8"));
    }

註意:不要用下面方式,這個方式是錯的,GMT-8最後獲取的時區還是0時區的。網上很多的教程說的是下面的方式,親測不行。

TimeZone tz = TimeZone.getTimeZone("ETC/GMT-8");
TimeZone.setDefault(tz);

在apprication.yml文件中配置一下數據庫連接信息,url加上這麼一句:
&serverTimezone=GMT%2b8

在這裡插入圖片描述

可以解決存入數據庫的時間肯定是對的,本地獲取的時間則未必是北京時間。將spring的json構造器的時區改正即可,在application.yml文件中添加:

在這裡插入圖片描述

或者可以使用註解,在entity實體類的date數據上添加註解,那麼數據庫傳回的data數據要轉換為json格式的時候就是北京時間瞭,再次傳回到前端的時候,也不會出現時區問題。

@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss",timezone="GMT+8")
 private Date lastTime;

不過,指的註意的是:這樣做,如果你的jvm時間依然是後臺0時區的,那麼後臺要用時間執行邏輯的時候,就要註意瞭,時間依然相差8小時,還是建議用第一方法,直接整個jvm改為北京的8時區。

總結:都是時區問題

三個問題對應三種場景:

  • 後臺要存時間到數據庫的時候:用方法2解決本地時間和數據庫時間的問題;本質是sql的服務器時區是0時區導致。
  • 後臺要使用本地時間的時候,改變jvm的時區;本質是jvm的時區是0時區導致。
  • 後臺返回數據到前端的時候出現時區問題,用註解或者yml中配置json生成器解決轉換格式的問題。本質是json的構造器用的時區是0時區導致。

到此這篇關於如何解決java獲取時間相差8小時的問題的文章就介紹到這瞭,更多相關java獲取時間相差8小時內容請搜索WalkonNet以前的文章或繼續瀏覽下面的相關文章希望大傢以後多多支持WalkonNet!

推薦閱讀: