Kuinka saan nykyisen unix-aikaleiman PostgreSQL: stä?

Unix-aikaleima on sekuntien lukumäärä keskiyöstä UTC: n jälkeen 1. tammikuuta 1970.

Kuinka saan oikean unix-aikaleiman PostgreSQL: stä?

Verrattaessa osoitteisiin currenttimestamp.com ja timestamp.1e5b.de En saa odotettua aikaa PostgreSQL: ltä:

Tämä palauttaa oikean aikaleiman:

SELECT extract(epoch from now()); 

Vaikka tämä ei olisikaan ”t:

SELECT extract(epoch from now() at time zone "utc"); 

Asun aikavyöhykkeellä UTC +02. Mikä on oikea tapa saada nykyinen unix-aikaleima PostgreSQL: stä?

Tämä palauttaa oikean ajan ja aikavyöhykkeen:

SELECT now(); now ------------------------------- 2011-05-18 10:34:10.820464+02 

Toinen vertailu:

select now(), extract(epoch from now()), extract(epoch from now() at time zone "utc"); now | date_part | date_part -------------------------------+------------------+------------------ 2011-05-18 10:38:16.439332+02 | 1305707896.43933 | 1305700696.43933 (1 row) Unix timestamp from the web sites: 1305707967 

vastaus

Postitiedostoissa timestamp with time zone voidaan lyhentää nimellä timestamptz ja timestamp without time zone nimellä timestamp. Käytän lyhyempiä tyyppinimiä yksinkertaisuuden vuoksi.

Unix-aikaleiman saaminen postgresistä timestamptz kuten now() on yksinkertainen, kuten sanot, vain:

select extract(epoch from now()); 

Se on oikeastaan kaikki mitä sinun tarvitsee tietää absoluuttisen ajan saamisesta mistä tahansa tyypistä timestamptz, mukaan lukien now().

Asiat monimutkaistuvat vain, jos sinulla on timestamp -kenttä .

Kun laitat timestamptz tietoja, kuten now() kyseiseen kenttään, ne muunnetaan ensin tietylle aikavyöhykkeelle. (joko nimenomaisesti at time zone -toiminnolla tai muuntamalla istunnon aikavyöhykkeeksi) ja aikavyöhyketiedot hylätään . Se ei enää viittaa absoluuttiseen aikaan. Siksi et yleensä halua tallentaa aikaleimoja nimellä timestamp ja normaalisti käyttäisit timestamptz – ehkä elokuva julkaistaan kello 18.00 tietyllä päivämäärä jokaisella aikavyöhykkeellä , se on sellainen käyttötapaus.

Jos työskentelet vain yhdellä aikavyöhykkeellä, saatat päästä eroon (väärin) käyttämällä timestamp. Muuntaminen takaisin muotoon timestamptz on tarpeeksi älykäs selviytymään DST: stä, ja muuntotarkoitusten oletetaan olevan aikaleimojen nykyisessä aikavyöhykkeessä. Tässä on esimerkki GMT / BST: stä:

select "2011-03-27 00:59:00.0+00"::timestamptz::timestamp::timestamptz , "2011-03-27 01:00:00.0+00"::timestamptz::timestamp::timestamptz; /* |timestamptz |timestamptz | |:---------------------|:---------------------| |2011-03-27 00:59:00+00|2011-03-27 02:00:00+01| */ 

DBFiddle

Huomaa kuitenkin seuraava hämmentävä käytös:

set timezone to 0; values(1, "1970-01-01 00:00:00+00"::timestamp::timestamptz) , (2, "1970-01-01 00:00:00+02"::timestamp::timestamptz); /* |column1|column2 | |------:|:---------------------| | 1|1970-01-01 00:00:00+00| | 2|1970-01-01 00:00:00+00| */ 

DBFiddle

Tämä johtuu siitä, että :

PostgreSQL ei koskaan tutki kirjaimellisen merkkijonon sisältöä ennen sen tyypin määrittämistä ja käsittelee näin ollen molempia […] aikaleimana ilman aikavyöhykettä. varmista, että kirjainta käsitellään aikaleimana aikavyöhykkeellä, anna sille oikea eksplisiittinen tyyppi … Kirjaimessa, joka on määritetty aikaleimaksi ilman aikavyöhykettä, PostgreSQL jättää huomiotta kaikki aikavyöhykeindikaatiot. c5aa40c735 ”>

Kommentit

  • Idea siitä, miten muunnetaan tuloksena oleva desimaali kokonaisluvuksi ilman desimaalipilkua (tarkoitan luvun ja desimaalin yhdistämistä muodossa yksi iso kokonaisluku). Kiitos.
  • Kuten tämä , mutta olen ' varma, ettet halua ' et todellakaan tehdä sitä. Ehkä haluat kertoa kymmenellä ja poistaa kaikki jäljellä olevat desimaalit?
  • @ W.M. Ehkä näin? SELECT FLOOR(EXTRACT(epoch FROM NOW())*1000);

vastaus

SELECT extract(epoch from now() at time zone "utc"); 

ei palauta oikeaa aikaleimaa, koska postgres-aikavyöhykkeen muunnos heittää pois aikavyöhyketiedot tuloksesta:

9.9.3. AIKAVYÖHYKKEELLÄ

Syntaksi: aikaleima ilman aikavyöhykettä TIME ZONE -vyöhykkeellä
Palauttaa: aikaleima aikavyöhykkeellä
Käsittele annettua aikaleimaa ilman aikavyöhykettä määritetyn aikavyöhykkeen sijaintina

Syntaksi: aikaleima aikavyöhykkeellä TIME ZONE -vyöhykkeellä
Palauttaa: aikaleima ilman aikavyöhykettä
Muunna annettu aikavyöhyke ja uusi aikavyöhyke ilman aikavyöhykettä.

jälkeenpäin ote tarkastelee aikaleimaa ilman aikavyöhykettä ja pitää sitä paikallisena ajankohtana (vaikka se onkin tosiasiallisesti jo utcaa).

Oikea tapa olisi:

select now(), extract(epoch from now()), -- correct extract(epoch from now() at time zone "utc"), -- incorrect extract(epoch from now() at time zone "utc" at time zone "utc"); -- correct now | date_part | date_part | date_part -------------------------------+------------------+------------------+------------------ 2014-10-14 10:19:23.726908+02 | 1413274763.72691 | 1413267563.72691 | 1413274763.72691 (1 row) 

Viimeisellä rivillä ensimmäinen at time zone suorittaa muunnoksen, seco Toinen määrittää tulokseen uuden aikavyöhykkeen.

Vastaa

Sähköpostiosoitettasi ei julkaista. Pakolliset kentät on merkitty *