2014-04-08 15 views
5

RethinkDB è un motore di database NoSQL meraviglioso e molto utile. Sto cercando il modo migliore per inserire oggetti datetime di Python. RethinkDB strorizza i timestamp UTC, quindi ho trovato una soluzione per convertire il mio oggetto datetime nel formato corretto.Qual è il modo migliore per inserire python datetime in rethinkdb?

Io uso questa funzione litle per convertire il mio oggetto datetime in somethink RethinkDB capire:

import calendar 
from datetime import datetime 
import rethinkdb as r 


def datetime_to_epoch_time(dt): 
    timestamp = calendar.timegm(dt.utctimetuple()) 
    return r.epoch_time(timestamp) 

title = u'foobar' 
published_at = '2014-03-17 14:00' 

# firts I convert 2014-03-17 14:00 to datetime 
dt = datetime.strptime(published_at, '%Y-%m-%d %H:%M') 

# then I store the result 
r.table('stories').insert({ 
    'title': title, 
    'published_at': datetime_to_epoch_time(dt), 
}).run() 

mio fuso orario corrente è CET (GMT + 2 ore) Si tratta di una buona soluzione per la memorizzazione le mie date in rethinkdb o esiste una soluzione migliore?

Grazie per il vostro aiuto

+2

Ho il sospetto che si sta memorizzare il momento sbagliato nel database. La riga 'dt = datetime.strptime (meta ['published_at'], '% Y-% m-% d% H:% M')' produrrà un oggetto datetime che è timezone naive come non hai specificato fuso orario ovunque. È in CET? È in UTC? Data questa ambiguità, cosa restituirà 'dt.utctimetuple()'? Se hai a che fare con i fusi orari, è meglio lavorare sempre con oggetti datetime con timezone. Per maggiori dettagli, date un'occhiata a [pytz] (http://pytz.sourceforge.net) – CadentOrange

+0

+1 per il commento sopra - memorizzate sempre i vostri dati in un formato che le informazioni sul fuso orario sono conservate. Anche se non si sta lavorando con dati di più paesi, l'ora legale potrebbe causare problemi. –

+0

Grazie, ora capisco l'importanza del fuso orario in datetime. – k3z

risposta

5

Un esempio con Pytz:

from datetime import datetime 
import pytz 

import rethinkdb as r 


# Init 
r.connect('localhost', 28015).repl() 
if 'test' in r.db_list().run(): 
    r.db_drop('test').run() 

r.db_create('test').run() 
r.db('test').table_create('stories').run() 

paris = pytz.timezone('Europe/Paris') 

r.table('stories').insert({ 
    'title': u'Foobar', 
    'published_at': paris.localize(datetime.strptime(
     '2014-03-17 14:00', '%Y-%m-%d %H:%M' 
    ), is_dst=False) 
}).run() 

for document in r.table("stories").run(): 
    print(document['published_at']) 
    print(type(document['published_at'])) 
+0

Per me questa sembra essere la soluzione migliore. Mi rendo conto che posso usare oggetti datetime nativi invece di convertirli in timestamp e mantenere il giusto fuso orario. pytz sembra incredibile – k3z

1

dt.utctimetuple() non converte un ingenuo dt a UTC fuso orario vale a dire, se published_at non è in UTC già allora restituisce il risultato sbagliato.

Se published_at è nel fuso orario locale e quindi dt è nel fuso orario locale:

from datetime import datetime 
import pytz # $ pip install pytz 
from tzlocal import get_localzone # $ pip install tzlocal 

tz = get_localzone() 
aware_dt = tz.localize(dt, is_dst=None) 
timestamp = (aware_dt - datetime(1970, 1, 1, tzinfo=pytz.utc)).total_seconds() 
# ... r.epoch_time(timestamp) 
+0

Grazie per questa soluzione. – k3z

Problemi correlati