2014-09-03 50 views
0

是否可以從Scala/Java(用於Cassandra中)在特定Unix時間戳中生成Type 1 UUID,以便可以使用它來獲取範圍記錄片段和表格中的單個記錄。以下結果似乎表明它可能是可能的。從Unix時間戳生成隨機Type 1 UUID以與Cassandra一起使用

import com.datastax.driver.core.utils._ 

var td = new DateTime(2003,1,1,0,0) 
val time_millis = td.getMillis() 
val lower = UUIDs.startOf(time_millis) 
val upper = UUIDs.endOf(time_millis) 

println(lower.getLeastSignificantBits()) # 9187201950435737472 
println(lower.getMostSignificantBits()) # -545498504376938025 
println(upper.getLeastSignificantBits()) # -9187201950435737471 
println(upper.getMostSignificantBits()) # -545455558998945321 

背景(如果存在要解決的問題一個更好的方法)。

我想批量導入幾千個車輛記錄到一個Cassandra數據庫。包含日期的列包含將車輛添加到原始數據庫(VCA)的日期,並且在特定日期通常不超過幾百次,這似乎表明在timeuuid中可用的熵可能足以解決此問題;即mac地址,小時,秒,...,100納秒和隨機部分。

示例查詢我需要執行

SELECT * FROM vehicles WHERE manufacturer = 'BMW'; 
SELECT * FROM vehicles WHERE manufacturer = 'BMW' AND id = a8bb5800-694c-11d7-8080-808080808080; 
SELECT * FROM vehicles WHERE manufacturer = 'BMW' AND id < a8bb5800-694c-11d7-8080-808080808080 AND id >= cb59c000-1c26-11d6-8080-808080808080; 

在CQL的表模式。

CREATE TABLE vehicles (
    id     timeuuid, 
    manufacturer  text, 
    model    text, 
    transmission  text, 
    description  text, 
    engine_capacity double, 
    fuel_type   text, 
    metric_urban  double, 
    metric_extra_urban double, 
    metric_combined double, 
    co2_g_per_km  double, 
    euro_standard  int, 
    noise    double, 
    co     double, 
    hc_nox    double, 
    hc     double, 
    nox    double, 
    particulates  double, 
    date_included  timestamp, 
    PRIMARY KEY (manufacturer, id) 
) WITH CLUSTERING ORDER BY (id ASC); 

同伴廠家表

SELECT * from manufacturers; 

CREATE TABLE manufacturers (
    id     uuid, 
    manufacturer  text, 
    years    set<int> 
    PRIMARY KEY (manufacturer, id) 
); 
+0

您的標題混淆詞'隨機'。 [版本1 UUID](http://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_.28MAC_address_.26_date-time.29)基於日期時間和MAC地址,128位中只有少數是隨機的。 [版本4](http://en.wikipedia.org/wiki/Universally_unique_identifier#Version_4_.28random.29)是幾乎完全隨機的類型。 – 2014-10-10 05:21:08

回答

3

我想這是可以做到的,在理論上。但是,沒有標準的Java API允許您在生成UUID時指定「當前時間」。

這不是打算如何使用類型1的UUID。 (不承擔Cassandra根據時間選擇「timeuuid」值的能力!)嵌入式時間戳是保證唯一性的方案的一部分......僅此而已。如果開始人爲地生成類型1的UUID的時間不同於當前的UUID,那麼您有(理論上的)問題,即您的「新」UUID實際上可能與該機器上真正創建的UUID相同;即您的UUID不再是唯一的。

如果我這樣做,我會生成UUID的正常方式,並將時間戳存儲在一個單獨的字段。


UPDATE

你也許能夠適應 「https://github.com/cowtowncoder/java-uuid-generator」 做你想做的。 (提示:寫一個棘手的「時間戳同步器」)。但我仍然認爲這是一個糟糕的主意。

+0

謝謝@stephen。按照您的建議,我最終使用了時間戳和類型4 UUID,並創建了一個由id索引的新查找表,查找參數(製造商,包含日期等)以從ID查詢主表。鑑於進口將是批量操作,重複/多重事實根源不應成爲太大的問題,並且我認爲這是一種習慣用語,因爲在Cassandra中建模關係時使用了類似的策略。 – Tds 2014-09-04 16:04:48

+0

我絕對同意,從UUID中提取日期時間是UUID目的的濫用。這種「聰明」常常導致麻煩。但是如果你堅持這樣做,至少要檢查[UUID的幾個可識別其版本的位](http://en.wikipedia.org/wiki/Universally_unique_identifier#Variants_and_versions)來驗證它確實是[版本1 ](http://en.wikipedia.org/wiki/Universally_unique_identifier#Version_1_.28MAC_address_.26_date-time.29)包含日期時間。所有版本都有128位,可以互相替換,所以不要假設UUID是版本1。 – 2014-10-10 05:25:43