在Cassandra CQL 3表定义中,我对静态和动态列混合有多少控制?

在Cassandra CQL 3表定义中,我对静态和动态列混合有多少控制?,cassandra,cql3,Cassandra,Cql3,我试图更好地理解在CQL3中,我可以将静态列和动态列混合在一起的级别。我在CQL3中创建了一个表来存储用户订阅数据,但我也在测试在表中存储租户id(带有二级索引)的方法,以便快速识别哪些用户属于哪些租户(租户是用户所属的更高级别实体) 我的create table语句如下,后面是一些伪数据插入: cqlsh:demodb> CREATE TABLE subscription_by_user ( user_id text, tenant

我试图更好地理解在CQL3中,我可以将静态列和动态列混合在一起的级别。我在CQL3中创建了一个表来存储用户订阅数据,但我也在测试在表中存储租户id(带有二级索引)的方法,以便快速识别哪些用户属于哪些租户(租户是用户所属的更高级别实体)

我的create table语句如下,后面是一些伪数据插入:

cqlsh:demodb> CREATE TABLE subscription_by_user (
              user_id text,
              tenant_id uuid,
              subscription_id int,
              type text,
              distribution int,
              PRIMARY KEY (user_id, subscription_id) );

cqlsh:demodb> CREATE INDEX subscription_ids ON subscription_templates_by_user (tenant_id);


cqlsh:demodb> INSERT INTO subscription_by_user (user_id, tenant_id, subscription_id, type, distribution) VALUES ('user1', f81d4fae-7dec-11d0-a765-00a0c91e6bf6, 2, 'MESSAGE', 4);

cqlsh:demodb> INSERT INTO subscription_by_user (user_id, tenant_id, subscription_id, type, distribution) VALUES ('user2', f81d4fae-7dec-11d0-a765-00a0c91e6bf6, 3, 'TOPIC', 5);

cqlsh:demodb> INSERT INTO subscription_by_user (user_id, tenant_id, subscription_id, type, distribution) VALUES ('user1', f81d4fae-7dec-11d0-a765-00a0c91e6bf6, 3, 'USER', 4);
这一切都很好,我使用cql 3 API得到了我所期望的结果:

cqlsh:demodb> SELECT * FROM subscription_by_user  ;

 user_id | subscription_id | distribution | tenant_id                            | type
---------+-----------------+--------------+--------------------------------------+------------
   user2 |               3 |            5 | f81d4fae-7dec-11d0-a765-00a0c91e6bf6 | TOPIC
   user1 |               2 |            4 | f81d4fae-7dec-11d0-a765-00a0c91e6bf6 | BOARD
   user1 |               3 |            4 | f81d4fae-7dec-11d0-a765-00a0c91e6bf6 | USER
但是,行的底层存储会导致Cassandra为每个新订阅复制租户id:

[default@demodb] list subscription_templates_by_user;
Using default limit of 100
Using default column limit of 100
-------------------
RowKey: user2
=> (column=3:, value=, timestamp=1366150799244000)
=> (column=3:distribution, value=00000005, timestamp=1366150799244000)
=> (column=3:tenant_id, value=f81d4fae7dec11d0a76500a0c91e6bf6, timestamp=1366150799244000)
=> (column=3:type, value=746573742d7479706532, timestamp=1366150799244000)
-------------------
RowKey: user1
=> (column=2:, value=, timestamp=1366150764854000)
=> (column=2:distribution, value=00000004, timestamp=1366150764854000)
=> (column=2:tenant_id, value=f81d4fae7dec11d0a76500a0c91e6bf6, timestamp=1366150764854000)
=> (column=2:type, value=746573742d74797065, timestamp=1366150764854000)
=> (column=3:, value=, timestamp=1366151741325000)
=> (column=3:distribution, value=00000004, timestamp=1366151741325000)
=> (column=3:tenant_id, value=f81d4fae7dec11d0a76500a0c91e6bf6, timestamp=1366151741325000)
=> (column=3:type, value=746573742d74797065, timestamp=1366151741325000)
我的问题是:有没有一种方法可以让我(使用CQL3)以每行只列出一次订阅id的方式构造表?如果没有,是否可以使用较旧的cassandra cli API执行此操作?这似乎是一个可行的用例,实际上是一个混合静态数据和动态数据(即订阅位)的问题,但我很可能是错的。我知道maps和其他CQL3集合类型是实现这一点的一种方法,但我必须立即检索整个集合这一事实让我有点紧张,如果我能帮助的话,我宁愿不将一些复杂的对象序列化到map值槽中


谢谢

如果不需要按订阅执行范围查询,或查询“用户X的所有订阅是什么”,则可以将其作为分区键的一部分:

CREATE TABLE subscription_by_user (
     user_id text,
     tenant_id uuid,
     subscription_id int,
     type text,
     distribution int,
     PRIMARY KEY ((user_id, subscription_id))
);

如果你真的需要这两样东西中的任何一个,那么就把它吸起来,并承担存储空间的罚款;大部分会被压缩掉。无论您使用的是CQL还是Thrift,这一点都是正确的。

为什么不考虑使用CQL3集合?复合分区键似乎是一个不错的选择。我一定是在文件里忽略了这一点。