2015-08-03 20 views
6

Ho bisogno di inviare dati in json. Quello che è importante è che voglio che le impostazioni internazionali siano preservate in modo che il destinatario ottenga la data nel suo fuso orario locale. Come lo posso fare?Come inviare java.util.Date in Json?

Non riesco a utilizzare semplicemente Date.toString() perché in quel caso non sarei in grado di analizzarlo sul lato ricezione se le impostazioni internazionali sono diverse (nomi di giorno e mese diversi e così via).

C'è una soluzione a questo?

risposta

1

Utilizzare il metodo getTime di java.util.Date per il timestamp. Una volta convertito in una data, ogni ricevitore può visualizzarlo usando il suo fuso orario locale.

Ricordate che Data

rappresenta un istante specifico nel tempo, con precisione millisecondo.

Il metodo toString appena formati che è in un specific way:

dow mon dd hh:mm:ss zzz yyyy 

Chosing per inviare il timestamp significa che si usa anche meno larghezza di banda.

+0

cosa succede quando la data viene creata in un fuso orario e passata e consumata in un altro fuso orario? – aviad

+0

La data creata in un fuso orario viene convertita nel numero di millisecondi dal 1 gennaio 1970, 00:00:00 GMT (via getTime) e quindi questo numero viene convertito in una data qualsiasi fuso orario. –

+0

Probabilmente è quello che sto cercando. Quanto è lungo il numero di millisecondi? – Greyshack

6

Un lungo intervallo di tempo dal 1970 va bene, ma non è leggibile dall'uomo, e quindi un PITA per test/sviluppo.

Quindi utilizzare il ISO 8601 tempo standard data"yyyy-MM-dd'T'HH:mm:ss" (dove 'T' è solo un letterale T (spesso si vede uno spazio qui;. E frazioni di secondo .SSS)

Tempo zona è possibile anche, ma si spera non necessario (= incorporato nel tempo localizzata).

Prima di Java 8 utilizzando SimpleDateFormat.

2

Il modo corretto per farlo è quello di scrivere la data in formato ISO 8601: cioè 2015-08-03T4:50:49+00:00

Non solo in include fuso orario ma anche qualsiasi decoder standard sul lato di ricezione della vostra JSON sarà in grado di decodificare senza i problemi.

Per la parte di invio, se si sta scrivendo la stringa da soli, anche solo formattarlo:

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

Ma se si sta utilizzando qualsiasi serializzatori JSON per trasformare da oggetti Java (come Jackson, per esempio), quindi basta rendere l'attributo dell'oggetto a java.util.Date e il serializzatore dovrebbe sapere cosa fare, data la configurazione corretta. Vedi this answer per Jackson, o this one per Jersey. Entrambi usano Joda Time.

0

Penso che ci sia il modo più semplice per fare questo,

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

tl; dr

Instant.now() 
     .toString() 

2017-01-23T12: 34: 56.123456789Z

UTC

Gene rally migliore per scambiare dati per i valori di data-ora in UTC (GMT). Lascia che il ricevitore si adatti al fuso orario desiderato.

Instant

La classe Instant rappresenta un momento sulla timeline in UTC, con una risoluzione di nanosecondi.

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

2017-01-23T12: 34: 56.123456789Z

Si può facilmente analizzare quella stringa.

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

ISO 8601

Lo standard definisce ISO 8601 chiare formati di facile lettura facili da analizzare per rappresentazioni testuali di valori di data e ora. Questi formati sono ideali per lo scambio di dati.

Per un momento in UTC, si intende il formato visto nell'esempio sopra. Lo T separa la parte della data dalla porzione dell'ora del giorno. Il Z alla fine è l'abbreviazione di Zulu e significa UTC.

Locale

La questione menziona locale come se relative al fuso orario. A Locale ha niente da fare con il fuso orario. A Locale specifica (a) la lingua umana per la traduzione di nome del giorno, nome del mese e simili, e (b) le norme culturali che decidono questioni di abbreviazione, lettere maiuscole, punteggiatura e così via.

Un fuso orario è una cronologia delle modifiche apportate a offset-from-UTC di una regione, con rilevamento di anomalie che hanno provocato tali modifiche, ad esempio Daylight Saving Time (DST).

Ricerca overflow per ulteriori informazioni. Questo è già stato coperto molte centinaia di volte. Cerca classi come ZoneId, ZoneOffset, ZonedDateTime, Instant, OffsetDateTime e DateTimeFormatter. Leggi lo Oracle Tutorial sulle classi java.time.

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

Prova questo formato: 2017-03-20T00: 00: 00,000 + 0100

+1

Quanto è diverso dalle altre risposte? –

0

Ci sono molti modi per farlo. Un modo per convertire la data in millisecondi che non dipende dalle impostazioni internazionali e usarla ulteriormente. Un altro modo per cambiare la data nel formato utc e usarlo ulteriormente. Se il fuso orario del tuo server è impostato su UTC java.util.Date funzionerà perfettamente perché prende il fuso orario di sistema per impostazione predefinita mentre utilizza la nuova data ("una certa data"). :

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

myDate sarà "Tue 6 giugno 05:30:00 UTC 2017", se fuso orario del sistema è UTC.

+0

Non sono d'accordo con tutti i punti. Un conteggio di millisecondi è ambiguo sia per la [data di riferimento dell'epoca] (https://en.wikipedia.org/wiki/Epoch_ (reference_date) #Notable_epoch_dates_in_computing) sia per la granularità (giorni, interi secondi, millisecondi, microsecondi, nanos) . Non esiste una cosa come "formato utc". Il fuso orario predefinito dell'OS host o della JVM è fuori dal controllo del programmatore e quindi inaffidabile; meglio specificare esplicitamente il fuso orario previsto/desiderato. La fastidiosa classe 'Date' usa un formato terribile, ed è ora legacy, soppiantata da' java.time.Instant'. –

Problemi correlati