使用 Cassandra 中的计数器进行数据建模,即将过期的列



这个问题是针对有经验的Cassandra开发人员的。我需要计算每个用户访问某些资源的次数和时间。我有这样的数据结构 (CQL):

CREATE TABLE IF NOT EXISTS access_counter_table (
  access_number counter,
  resource_id varchar,
  user_id varchar,
  dateutc varchar,
  PRIMARY KEY (user_id, dateutc, resource_id)
);

我需要获取有关用户在过去 N 天内访问资源的次数的信息。因此,为了获得最后 7 天,我提出这样的请求:

SELECT * FROM access_counter_table
  WHERE
    user_id = 'user_1'
    AND dateutc > '2015-04-03'
    AND dateutc <= '2015-04-10' ;

我得到这样的东西:

user_1 : 2015-04-10 : [resource1:1, resource2:4]
user_1 : 2015-04-09 : [resource1:3]
user_1 : 2015-04-08 : [resource1:1, resource3:2]
...

所以,我的问题是:旧数据必须在一段时间后删除,但 Cassandra 不允许设置 EXPIRE TTL 来对抗表

我每小时有数百万个访问事件(可能数十亿个)。7天后,这些记录将毫无用处。

  • 如何清除它们?或者在卡桑德拉制作类似垃圾收集器的东西?这是一个好方法吗?
  • 也许我需要为此使用另一个数据模型?会是什么?

谢谢。

正如你所发现的,Cassandra 不支持计数器列上的 TTL。事实上,在 Cassandra 中的计数器上进行删除通常是有问题的(一旦你删除了一个计数器,你基本上不能在一段时间内重用它)。

如果需要自动过期,可以使用 int 字段对其进行建模,也可以使用外部锁定(例如 zookeeper)、请求路由(仅允许一个写入器访问特定分区)或轻量级事务来使用 TTL 安全地递增该整数字段。

或者,您可以分页浏览计数器表,并在计划任务上使用 DELETE 手动删除"旧"计数器。这不太优雅,也不能缩放,但在某些情况下可能有效。

最新更新