2

astyanax クライアントを使用して複合キーを持つテーブルを作成するにはどうすればよいですか。今のところ、cqlsh -3 で作成しました。cli では次のようになります。

[default@KS] describe my_cf;
    ColumnFamily: my_cf
      Key Validation Class: org.apache.cassandra.db.marshal.UTF8Type
      Default column value validator: org.apache.cassandra.db.marshal.UTF8Type
      Columns sorted by: org.apache.cassandra.db.marshal.CompositeType(org.apache.cassandra.db.marshal.TimeUUIDType,org.apache.cassandra.db.marshal.UTF8Type)
      GC grace seconds: 864000
      Compaction min/max thresholds: 4/32
      Read repair chance: 0.1
      DC Local Read repair chance: 0.0
      Replicate on write: true
      Caching: KEYS_ONLY
      Bloom Filter FP chance: default
      Built indexes: []
      Compaction Strategy: org.apache.cassandra.db.compaction.SizeTieredCompactionStrategy
      Compression Options:
        sstable_compression: org.apache.cassandra.io.compress.SnappyCompressor

これは、cqlshにあると私が期待する方法です:

 CREATE TABLE my_cf (
                   ... key text,
                   ... timeid timeuuid,
                   ...   flag boolean,
                   ...   data text,
                   ... PRIMARY KEY (key, timeid));

問題であるブロブとして保存された複合キーで動作するようになりました。

私のコード

public class MyKey {
    @Component(ordinal=0)
    private String key;
    @Component(ordinal=1)
    private UUID timeid;
 //...
}

CF

public static ColumnFamily<MyKey, String> MY_CF = ColumnFamily
        .newColumnFamily("my_cf",
                new AnnotatedCompositeSerializer<MyKey>(MyKey.class),
                StringSerializer.get());

KS

                ksDef = cluster.makeKeyspaceDefinition();

                ksDef.setName(keyspaceName)
                        .setStrategyOptions(keyspaceOptions)
                        .setStrategyClass("SimpleStrategy")
                        .addColumnFamily(
                                cluster.makeColumnFamilyDefinition()
                                        .setName(MY_CF.getName())
                                        .setComparatorType("UTF8Type")
                                        .setDefaultValidationClass("UTF8Type")
// blob if no key validation class specified
// and something looking as a string if I use this:     .setKeyValidationClass("CompositeType(UTF8Type, TimeUUIDType)")
// anyway there's a single column per composite key

                                        .addColumnDefinition(
                                                cluster.makeColumnDefinition()
                                                        .setName("flag")
                                                        .setValidationClass(
                                                                "BooleanType"))
                                        .addColumnDefinition(
                                                cluster.makeColumnDefinition()
                                                        .setName("data")
                                                        .setValidationClass(
                                                                "UTF8Type")));
                cluster.addKeyspace(ksDef);

突然変異

            MutationBatch m = ks.prepareMutationBatch();

            for (char keyName = 'A'; keyName <= 'C'; keyName++) {
                MyKey myKey = new MyKey("THEKEY_" + keyName, TimeUUIDUtils.getUniqueTimeUUIDinMillis());
                ColumnListMutation<String> cfm = m.withRow(MY_CF, myKey);
                cfm.putColumn("flag", true, null);
                cfm.putColumn("data", "DATA_" + keyName, null);
            }
            m.execute();

cqlsh:KS>describe columnfamily my_cf;

CREATE TABLE my_cf (
  KEY blob PRIMARY KEY,
  flag boolean,
  data text
) WITH ...

cqlsh:KS>select * from my_cf;

  key                                                      | flag | data
----------------------------------------------------------+--------+---------
 00064953494e5f420000109f4513d0e3ac11e19c400022191ad62b00 | True   | DATA_B

cqlsh:KS> select * from my_cf where key = 'THEKEY_B' order by timeid desc;

Bad Request: Order by on unknown column timeid

以下のcassandra-cliで正しく見えませんか?cqlsh で動作しないのはなぜですか?

cassandra-cli] リスト my_cf;

RowKey: THEKEY_B:09f29941-e3c2-11e1-a7ef-0022191ad62b
=> (column=active, value=true, timestamp=1344695832788000)
=> (column=data, value=DATA_B, timestamp=1344695832788000)

私は何を間違っていますか?(astyanax 1.0.6、カサンドラ 1.1.2) cqlsh>[cqlsh 2.2.0 | カサンドラ 1.1.2 | CQL 仕様 3.0.0 | 倹約プロトコル 19.32.0]

4

1 に答える 1

4

私が把握できたことから、複合主キーはプロトコルと cassandra へのインターフェースの大きな相違点を表し、使用するプロトコルはアクセスできる機能を制御します。

たとえば、astyanax と hector は主に thrift プロトコル クライアントですが、CQL は単なる言語ではなく、バイナリ プロトコルです (またはそうなる予定ですか?)。

この 2 つのプロトコルは同等ではなく、複合主キーを使用する CQL3 では状況が大きく異なります。

複合主キーを持つ「TABLES」について理解しておくべきことは、基本的に複合列名を持つ幅の広い行に変換されるということです。主キーの最初の部分は行キーで、残りの部分はプレフィックスとして使用され、幅の広い行の列名としての TABLE 列名と共に使用されます。

インスタンスでは、行キーは「キー」で、列のプレフィックスは「timeid」であるため、挿入するもののフラグ フィールドは実際には :flag という名前の列であり、データは :data などです。

これを機能させるために、cassandra への CQL プロトコル インターフェイスは、「TABLES」を幅の広い行に変換し、その列の命名をすべて透過的に処理します。

thrift インターフェイスはこのようなことを処理せず、ミューテーションを行うと、仮想アドレッシングなしで、慣れ親しんだように列を書き込むだけです。

したがって、実際には、cassandra-cli で結果が正しく表示されません。cqlsh -3 から挿入すると、cassandra-cli の観点からは次のようになります (単純なテキストの日付を使用)。

[default@testapp] list my_cf;
RowKey: mykey
=> (column=20120827:data, value=some data, timestamp=1346090889361000)
=> (column=20120827:flag, value=, timestamp=1346090889361001)

CQL3 とテーブルは非常に魅力的に見えますが、いくつかのトレードオフが必要であり、Java クライアントの確実なサポートはまだないようです。

于 2012-08-27T18:26:09.980 に答える