如何对表进行建模以根据状态字段(随时间而变化)运行查询

时间:2018-12-20 00:08:45

标签: cassandra cassandra-2.0 cassandra-3.0

当前,我们有一个表,可以使用shipping_id查询,将来我们需要根据状态字段进行查询 当前表:

CREATE TABLE shipment ( 
    shipment_id text,
    tenant_id text,
    actual_arrival_time text,
    actual_dep_time text,
    email_ids set,
    is_deleted boolean,
    modified_by text,
    modified_time timestamp,
    planned_arrival_time text,
    planned_dep_time text,
    route_id text,
    shipment_departure_date text,
    status_code text,
    PRIMARY KEY (shipment_id, tenant_id) 
); 

CREATE INDEX shipment_id_index ON shipment (tenant_id);

当前查询的

1)选择*从发运中tenant_id =?0允许过滤;

2)SELECT * FROM货件WHEREship_id =?0和tenant_id =?1;

待处理/将来查询的

到目前为止,

给定状态码的货件ID列表 3)选择*从货件中,tenant_id ='y'和status_code = x吗? ;

4)过去1周内给定状态码的货件ID列表

5)延误的货件ID列表

上表可能有10-15个唯一的租户  并将有1个shipping_id,1个tenant_id每张表1行 随着运输的进行,状态码将随着时间的推移而变化,从Shipment_started,shipping_progress,shipping_delayed,shipping_delayed_completed和shipping_completed等 生命周期中的每批货物都会经过3-5种状态,当前表格 仅当给定的shipment_id的状态发生变化时,才会更新。

我需要创建一个新表来解决查询的问题

3)到现在为止具有status_code ='x'的给定租户的货运清单

4)给定租户的过去1周内status_code ='x'的货件清单

5)延误的发货清单?

1 个答案:

答案 0 :(得分:2)

在Cassandra中,您可以根据查询对表进行建模,因此实际上可以为可能执行的每个查询创建一个表。在查询中也使用ALLOW FILTERING是只用于开发和测试目的,而不是在实际的生产应用程序中使用(请在此处查看答案:Cassandra CQLEngine Allow Filtering)。

因此,对于您提到的每种情况/查询,我都建议:

1) SELECT * FROM shipment where tenant_id=?0 ALLOW FILTERING;

这应该通过下表解决:

CREATE TABLE shipment ( 
    tenant_id text,
    shipment_id text,
    actual_arrival_time text,
    actual_dep_time text,
    email_ids set,
    is_deleted boolean,
    modified_by text,
    modified_time timestamp,
    planned_arrival_time text,
    planned_dep_time text,
    route_id text,
    shipment_departure_date text,
    status_code text,
    PRIMARY KEY (tenant_id, shipment_id) 
);

这里tenant_idpartition key,因此,如果您执行查询:SELECT * FROM shipment where tenant_id='x'; 那么您就无需再使用ALLOW FILTERING

更新:我还添加了shipment_id作为主键的一部分,以处理相同的cardinality,以防tenant_id不唯一,从而{@ {1}}由primary keytenant_id组成,以避免按照@Himanshu Ahire的注释覆盖具有相同shipment_id的记录。

tenant_id

这应该通过下表解决:

2)SELECT * FROM shipment WHERE shipment_id='x' and tenant_id='y';

此处CREATE TABLE shipment ( shipment_id text, tenant_id text, actual_arrival_time text, actual_dep_time text, email_ids set, is_deleted boolean, modified_by text, modified_time timestamp, planned_arrival_time text, planned_dep_time text, route_id text, shipment_departure_date text, status_code text, PRIMARY KEY ((shipment_id, tenant_id)) ); shipment_id都用作composite partition key

tenant_id

3) SELECT * FROM shipment WHERE tenant_id = 'y' and status_code = 'x';

4) list of shipment id's for given status code for last 1 week

这些应通过下表解决:

5) list of shipment id's for which got delayed

在这里,您还应该同时将CREATE TABLE shipment ( status_code text, tenant_id text, shipment_id text, actual_arrival_time text, actual_dep_time text, email_ids set, is_deleted boolean, modified_by text, modified_time timestamp, planned_arrival_time text, planned_dep_time text, route_id text, shipment_departure_date text, PRIMARY KEY ((tenant_id, status_code), actual_arrival_time) ) WITH CLUSTERING ORDER BY (actual_arrival_time DESC); tenant_id用作status_code,将composite partition key用作actual_arrival_time 因此您可以轻松创建查询,例如:

clustering column

3) SELECT * FROM shipment WHERE tenant_id = 'y' and status_code = 'x';

4) SELECT * FROM shipment WHERE tenant_id = 'y' and status_code = 'x' and actual_arrival_time >= 'date of last week';

仅作为查询编号4的注释,您可以从应用程序代码或使用cql functions

发送上周的日期