2015-08-03 23 views
6

我需要在JSON發送數據。重要的是,我希望保留區域設置,以便接收方在當地時間獲取日期。我怎樣才能做到這一點?如何在Json中發送java.util.Date?

我不能簡單地使用Date.toString(),因爲如果它們的語言環境不同(不同日期和月份名稱等),那麼我將無法在接收端解析它。

有沒有解決方案?

回答

1

使用java.util.Date的getTime方法爲時間戳。一旦您將其轉換回日期,每個接收器都可以使用當地時區顯示。

記住日期

表示特定的瞬間,精確到毫秒。

toString方法只是格式化它在specific way

dow mon dd hh:mm:ss zzz yyyy 

艇員選拔髮送時間戳意味着你還可以使用更少的帶寬。

+0

當在一個時區中創建並在另一個時區傳遞並消耗的日期時會發生什麼? – aviad

+0

在時區中創建的日期轉換爲自1970年1月1日00:00:00 GMT(通過getTime)以來的毫秒數,然後將該數字轉換爲任何時區的日期。 –

+0

這可能是我在找的東西。毫秒數是多少? – Greyshack

6

自1970年以來,很長一段時間的ms很好,但不是人類可讀的,因此是用於測試/開發的PITA。

因此使用ISO 8601標準日期時間"yyyy-MM-dd'T'HH:mm:ss"(其中'T'只是一個文字T(一個經常在這裏看到了空間;和分數秒.SSS

時間也是可能的,但希望不需要(=在本地化時間併入)。

使用SimpleDateFormat的java 8之前。

2

做到這一點,正確的方法是寫你的日期ISO 8601格式: 即2015-08-03T4:50:49+00:00

不僅將包括時區還要看你的JSON的接收端的任何標準解碼器將能夠毫不解碼問題。

對於發送部分,如果你自己寫的字符串,也只是將其格式化:

ZonedDateTime.now(ZoneId.systemDefault()) 
      .format(DateTimeFormatter.ISO_DATE_TIME) 

但如果你使用任何JSON序列化從Java對象變換(如傑克遜例如)那麼只要使對象屬性爲java.util.Date,並且在給定正確設置的情況下,串行器應該知道該做什麼。請參閱新澤西this answer傑克遜,或this one。他們都使用喬達時間。

0

我認爲這是簡單的方式做到這一點,

DateFormat dateFormat=new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ"); 
yourJsonObject.accumulate("yourDateVarible",dateFormat.format(new Date())); 
2

TL;博士

Instant.now() 
     .toString() 

2017-01-23T12:34:56.123456789Z

UTC

基因最好以UTC(GMT)交換日期時間值的數據。讓接收器調整到所需的時區。

Instant

Instant類表示UTC時間線與納秒的分辨率上一會兒。

Instant instant = Instant.now() ; 
String output = instant.toString() ; // Generate a String in standard ISO 8601 format. 

2017-01-23T12:34:56.123456789Z

您可以輕鬆地分析該字符串。

Instant instant = Instant.parse("2017-01-23T12:34:56.123456789Z") ; 

ISO 8601

ISO 8601標準定義清晰易於閱讀易於解析格式的日期時間值的文本表示。這些格式非常適合數據交換。

在UTC的片刻,這意味着上面的例子中看到的格式。 T將日期部分與時間部分分開。 Z最後是Zulu的縮寫,意思是UTC。

區域設置

該問題提到區域設置,就好像與時區相關。 A Locale沒有與時區有關。 A Locale指定(a)用於翻譯日期名稱,月份名稱等的人類語言,以及(b)用於確定縮寫,大寫,標點符號等問題的文化規範。

時區是一個地區的offset-from-UTC的變化歷史,跟蹤導致這些變化的異常,如Daylight Saving Time (DST)

搜索堆棧溢出以瞭解更多信息。這已經被覆蓋了數百次了。搜索類別,例如ZoneId,ZoneOffset,ZonedDateTime,Instant,OffsetDateTimeDateTimeFormatter。閱讀關於java.time類的Oracle Tutorial

ZonedDateTime zdt = instant.atZone(ZoneId.of("Pacific/Auckland")) ; 
-1

試試這個格式: 2017-03-20T00:00:00.000 + 0100

+1

與其他答案有何不同? –

0

有很多方法可以做到這一點。 以毫秒爲單位轉換不依賴區域設置並進一步使用的日期的一種方法。 以utc格式更改日期並進一步使用它的另一種方法。如果服務器的時區設置爲UTC,則java.util.Date將完美工作,因爲在使用新Date(「some date」)時,默認情況下系統時區需要使用。 :

long lastAccessedDate = 110002028250; 
    String myDate = new java.util.Date(lastAccessedDate()).toString(); 

如果系統時區爲UTC,myDate將爲「星期二06 06 05:30:00 UTC 2017」。

+0

我必須不同意你的觀點。對於[時期參考日期](https://en.wikipedia.org/wiki/Epoch_(reference_date)#Notable_epoch_dates_in_computing)和粒度(天,整秒,毫秒,微秒,納米)而言,毫秒數是不明確的。 。沒有'utc格式'這樣的東西。主機OS或JVM的默認時區不在編程器的控制範圍內,因此不可靠;更好地明確指定您的預期/所需時區。麻煩的Date類使用了一種糟糕的格式,現在是遺留的,被java.time.Instant代替。 –