2012-06-22 45 views
0

我在「歐洲/倫敦」時區有一個數據庫服務器,在「歐洲/布魯塞爾」有我的網絡服務器。由於現在是夏令時,我的應用服務器有2小時不同。MySQL數據庫服務器在不同時區的JDBC JDBC日期問題

我創建了一個測試,以重現我的問題:

Query q = JPA.em().createNativeQuery("SELECT UNIX_TIMESTAMP(startDateTime) FROM `Event` WHERE `id` =574"); 
BigInteger unix = (BigInteger) q.getSingleResult(); 
System.out.println(unix + "000 UNIX_TIMESTAMP to BigInteger"); 

Query q2 = JPA.em().createNativeQuery("SELECT startDateTime FROM `Event` WHERE `id` =574"); 
Timestamp o = (Timestamp) q2.getSingleResult(); 
System.out.println(o.getTime() + " Timestamp"); 

的的startDateTime列被定義爲「日期時間」(但同樣的問題與「時間戳」) 我得到的輸出是這樣的:

1340291591000 UNIX_TIMESTAMP to BigInteger 
1340284391000 Timestamp 

閱讀java日期對象導致時區轉變,我該如何解決這個問題?我期望jdbc驅動程序只需設置它從Date對象中的服務器獲得的「unix time」值。

(一個妥善的解決辦法應該與任何時區組合工作,不僅爲GMT DB)

+0

什麼數據庫數據類型是你的'startDateTime'字段? – Olaf

+0

我認爲UNIX_TIMESTAMP值與System.currentTimeMillis()不一樣,需要在UNIX_TIMESTAMP(毫秒)到Java的毫秒錶示之間進行某種轉換。檢查這個鏈接:http://stackoverflow.com/questions/3188425/java-date-format-conversion –

+0

我知道它是不一樣的,讓我修復這個例子,它不是關於最後的零。 @Olaf startDateTime列被定義爲'datetime'但'timestamp'我有同樣的問題 – Somatik

回答

0

我能解決這個問題,用連接字符串參數

useJDBCCompliantTimezoneShift=true&useSSPSCompatibleTimezoneShift=true 

,但我不是100%舒服這個,因爲它會導致當數據庫是不是在UTC/GMT時區就更麻煩了。

1

JDBC驅動程序使用的是它在運行JVM時區設置。如果你正在運行的應用程序歐洲/布魯塞爾,它假定時區。如果您的數據庫服務器正在另一個時區運行,Java中計算的結果可能與SQL中計算結果不同。

+0

對我來說沒有意義,從服務器查詢數據時絕對日期(unix時間)應該保持不變,我需要修正這個問題。 – Somatik

+0

我很欣賞你的幽默感!您始終可以將unix時間存儲爲長整數。 DATETIME數據類型在我知道的所有數據庫中都被破壞。時間戳(或因爲它在許多其他數據庫調用,TIMEZONE TIMESTAMP)本來是要解決這個問題,但依靠DATETIME數據類型的十年裏留下這麼多的開發者感到困惑的事情是如何工作的,那好運氣使得它,除非你的工作控制數據源和消費者的代碼。 – Olaf

0

你可以設置MySQL的時間戳列類型和:

<bean id="dataSource" class="com.jolbox.bonecp.BoneCPDataSource" destroy-method="close"> 
    <property name="driverClass" value="com.mysql.jdbc.Driver"/> 
    <property name="jdbcUrl" value="${jdbc.url}"/> 
    <property name="username" value="${jdbc.user}"/> 
    <property name="password" value="${jdbc.pass}"/> 
    <property name="idleConnectionTestPeriodInMinutes" value="60"/> 
    <property name="idleMaxAgeInMinutes" value="240"/> 
    <property name="maxConnectionsPerPartition" value="30"/> 
    <property name="minConnectionsPerPartition" value="10"/> 
    <property name="partitionCount" value="3"/> 
    <property name="acquireIncrement" value="5"/> 
    <property name="statementsCacheSize" value="100"/> 
    <property name="initSQL" value="SET time_zone='${database.timezone}'"/> 

這是我bonecp數據源 - >看到initSQL此查詢每個MySQL連接的初始化執行。如果您的網絡服務器在歐洲/布魯塞爾將此時區設置爲$ {database.timezone},則適用於我。 如果你的MySQL有空的時區表,你neeads導入它構成了Linux語言環境中,如:

mysql_tzinfo_to_sql在/ usr/share/zoneinfo中| mysql -u root -p mysql

相關問題