Cassandra:插入值并更新平均值/最小值/最大值

时间:2016-10-17 23:17:17

标签: cassandra cql

我正在考虑在Java应用程序中使用Cassandra作为时间序列数据。我还需要最后 n 分钟的平均值(和最小值/最大值)。

简单的方法是从客户端进行三次调用:

  1. 插入新值
  2. 选择最近 n 分钟
  3. 的平均值,最小值和最大值
  4. 更新平均值
  5. 有更有效的方法吗?

    第一步和第二步使用相同的分区,因此将在同一节点上运行。因此,如果两个语句都可以在同一请求中执行,则可以保存往返。但BATCH不支持select(据我所知)。

    第三个请求涉及不同的分区(因此可能是不同的节点)。使用BATCH的好处是两个表保持同步。我认为这也可以节省客户 - >协调员往返。但BATCH不支持将结果从选择传递到更新(据我所知)。

    create table metrics (
      resource_name text,
      metric_name text,
      recorded_at timestamp,
      value double,
      primary key ((resource_name, metric_name), recorded_at)
    ) with clustering order by (recorded_at desc);
    
    create table last_30m (
      metric_name text,
      resource_name text,
      avg_value double,
      min_value double,
      max_value double,
      primary key (metric_name, resource_name)
    ) with clustering order by (resource_name asc);
    

1 个答案:

答案 0 :(得分:2)

有一个avgminmax聚合函数(截至2.2)。所以你真的不需要一个表,你可以只查询它。自recorded_at

排序后,数据将全部按顺序存储在磁盘或memtables中

SELECT avg(value), min(value), max(value) FROM metrics WHERE resource_name = 'blarg' AND metric_name = 'cpu' AND recorded_at > {half hour ago}

将来会有一个now()-30m(CASSANDRA-11936)但是现在你必须手动计算并将“半小时前”值放入其中。

我强烈建议避免使用BATCH并为此更新第二个表,并让查询在需要时读取值。如果您担心上述查询的性能,请在进行优化之前对其进行测试,这种优化很可能会更加昂贵。如果你需要像“过去一天的平均值”这样的东西,它可能是值得的,但我不会把它作为你的更新的一部分而是更多的“每分钟更新”有点事(也考虑火花流)