2013-05-13 72 views
9

重要 如果你這個問題今天處理,使用來自datastax(即進口卡桑德拉)新卡桑德拉驅動程序,因爲它解決了這個最常見的問題和唐不再使用舊的cql驅動程序,它已經過時了!這個問題在新驅動程序甚至處於開發階段之前就已經陳舊了,我們不得不使用一個名爲cql的不完整的舊庫(導入cql < - 不要再使用它,轉到新的驅動程序)。如何插入日期時間爲卡桑德拉1.2時間戳列

簡介 我正在使用python庫cql來訪問Cassandra 1.2數據庫。在數據庫中,我有一個帶有時間戳列的表格,在我的Python代碼中,我有一個日期時間插入列中。舉例如下:

CREATE TABLE test (
    id text PRIMARY KEY, 
    last_sent timestamp 
); 

代碼

import cql 
import datetime 
... 
cql_statement = "update test set last_sent = :last_sent where id =:id" 
rename_dict = {} 
rename_dict['id'] = 'someid' 
rename_dict['last_sent'] = datetime.datetime.now() 
cursor.execute (cql_statement, rename_dict) 

問題

當我執行代碼執行的實際CQL語句是這樣:

update test set last_sent =2013-05-13 15:12:51 where id = 'someid' 

然後失敗,錯誤

Bad Request: line 1:XX missing EOF at '-05' 

這個問題似乎是在CQL庫沒有逃脫(「」),或在運行查詢之前轉換的日期時間。

問題 什麼是做,而無需手動逃逸的日期,並能完整的時間戳更精確地存儲到卡桑德拉時間戳列的正確方法是什麼?

在此先感謝!

回答

7

已ABHI已經指出這可以通過使用毫秒紀元以來從cqlsh長值來實現,現在我們需要讓它工作在Python代碼。

使用cql庫時,此轉換(從datetime到epoch以來的毫秒數)不會發生,因此爲了使更新正常工作,並且仍然具有將日期時間轉換爲自紀元以來的毫秒數所需的精度。

來源 使用這個有用的問題:Getting millis since epoch from datetime,尤其在該函數(請注意我做了一點變化):

解決方案

import datetime 

def unix_time(dt): 
    epoch = datetime.datetime.utcfromtimestamp(0) 
    delta = dt - epoch 
    return delta.total_seconds() 

def unix_time_millis(dt): 
    return long(unix_time(dt) * 1000.0) 

在這個例子中的代碼將:

cql_statement = "update test set last_sent = :last_sent where id =:id" 
rename_dict = {} 
rename_dict['id'] = 'someid' 
rename_dict['last_sent'] = unix_time_millis(datetime.datetime.now()) 
cursor.execute (cql_statement, rename_dict) 

您可以將日期時間轉換爲包含自時代以來的毫秒數的長整型值,這就是所有更新將使用長整型值轉換爲等效表單的時間戳。

希望它可以幫助別人

10

我可以告訴你如何在cqlsh中做到這一點。試用日期時間2013-05-13 15:12:51

update test set last_sent =1368438171000 where id = 'someid' 

等效長值1368438171000

+1

感謝abhi,這正是我所要求的。我會在幾個發佈完整的答案。 – 2013-05-14 15:54:11

5

那麼對我來說,與

update test set last_sent = '2013-05-13 15:12:51' where id = 'someid' 

直接作用無需轉換的東西。因此,在Python中可以使用datetime值作爲字符串做:

cursor.execute("UPDATE test SET ts=:ts WHERE id=:id;", 
    dict(ts=your_datetime.isoformat(), id=id)) 
+0

當這個問題發佈時,這不起作用,這就是爲什麼我問。你能否提供更多關於你正在使用的cql庫版本的信息? – 2013-10-07 17:39:06

+0

Cassandra 2與CQL3,抱歉不提這個,只是想在這裏發佈這個方法給別人。 – webjunkie 2013-10-08 09:47:46

+0

沒關係,問題是你的答案是針對不同的問題,你在第一個代碼塊上寫的更新是用在cqlsh上的並且是CQL(Cassandra查詢語言)語句,問題是關於如何執行該查詢從python使用python cql庫(而不是cassandra查詢語言)。 – 2013-10-24 20:32:05

1

大部分的解決方案是有效的,我只是想提出一個簡單的辦法:

from datetime import datetime 

my_date = int(float(datetime.now().strftime("%s.%f"))) * 1000 

update test set last_sent = my_date where id = 'someid' 
+0

將日期轉換爲長的任何類型都是有效的,所以它也應該起作用。爲了讀者的利益,只需使用datastax中的新cassandra驅動程序,因爲它解決了大多數常見問題,不再使用舊的cql驅動程序,它已經過時了! – 2015-10-21 22:13:17

1

我知道這是一個2歲的問題,但如果有人來尋找答案,使用日期時間實例,而不是使用時間戳。不過,Python驅動應該巧妙地處理一個整數/浮點數。

+0

是zonked,問題來自於datastax的新python驅動程序甚至存在之前(這解釋了代碼中的導入cql)。儘管如此,問題中的時間戳是指Cassandra類型的時間戳,cassandra中沒有日期時間類型。正如你所看到的,python代碼已經在使用datetime。所以你的答案應該是「使用新的驅動程序」。仍然是一個有效的點 – 2016-04-25 17:08:49