2

次の列ファミリーに時系列データを保存しようとしています。

create column family t_data with comparator=TimeUUIDType and default_validation_class=UTF8Type and key_validation_class=UTF8Type;

私はこの方法でデータを正常に挿入しています:

data={datetime.datetime(2013, 3, 4, 17, 8, 57, 919671):'VALUE'}
key='row_id'
col_fam.insert(key,data)

ご覧のとおり、datetimeオブジェクトを列名として使用すると、pycassaはtimeUUIDオブジェクトに正しく変換されます。

[default@keyspace] get t_data[row_id];

=> (column=f36ad7be-84ed-11e2-af42-ef3ff4aa7c40, value=VALUE, timestamp=1362423749228331)

場合によっては、アプリケーションが一部のデータを更新する必要があります。問題は、同じ日時オブジェクトを渡してその列を更新しようとすると、pycassaが別のUUIDオブジェクト(時間部分は同じ)を作成するため、列を更新する代わりに別のUUIDオブジェクトを作成することです。

[default@keyspace] get t_data[row_id];

=> (column=f36ad7be-84ed-11e2-af42-ef3ff4aa7c40, value=VALUE, timestamp=1362423749228331)

=> (column=**f36ad7be**-84ed-11e2-b2fa-a6d3e28fea13, value=VALUE, timestamp=1362424025433209)

問題は、日時オブジェクトを渡すpycassaでTimeUUIDベースの列を更新するにはどうすればよいですか?または、これが正しい方法ではない場合、推奨される方法は何ですか?

4

1 に答える 1

2

リードモディファイライトを行わない限り、できません。UUIDは本質的に一意です。これらは、時系列で並べ替える一意のIDを取得する方法の問題を解決するために存在しますが、同時に、まったく同時に発生することの衝突を回避します。

したがって、その列を更新するには、最初にその列を読み取る必要があります。これにより、その列キーを見つけ、その値を変更して、再度書き戻すことができます。

これは特に洗練されたソリューションではありません。Cassandraではread-modify-writeを実際に避ける必要があります。おそらく、TimeUUIDは列キーに適切なタイプではありませんか?あるいは、戻って変更する必要がないようにアプリケーションを設計する別の方法があるかもしれません。

クエリパターンがどのように見えるかを知らなければ、代わりに何をすべきかを正確に言うことはできませんが、うまくいけば関連するいくつかの提案があります:

値を更新するのではなく、新しい値を書き込むだけです。時間Tで何かが真だった場合、時間T + 1で変化したとしても、時間Tは常に真でした。物事が変化したときは、変化の時間とともに新しい値を書き込み、古い値をそのままにします。タイムラインを読むときは、最新の値を選択することでこれらの競合を解決します。値は時系列で並べ替えられるため、常に最新の値が最後の値になります。これは、Cassandraが内部で行う方法と非常によく似ており、非常に強力なパターンです。

これにより、より多くのディスクスペースが消費されたり、時系列を読み取るときに追加のCPUが必要になることを心配する必要はありません。他の方法で実装する必要がある読み取り、変更、書き込みの複雑さに比べると、おそらく小さいでしょう。

問題を解決する方法は他にもあるかもしれません。詳細を教えていただければ、より適切な方法を考え出すことができます。

于 2013-03-05T09:14:02.113 に答える