【问题标题】:Transaction `Check and Insert` on CassandraCassandra 上的事务“检查和插入”
【发布时间】:2021-11-19 17:33:26
【问题描述】:
CREATE TABLE table (
  id1 uuid,
  bucket timestamp,
  createdat timestamp,
  id2 uuid,
  data blob,
  
  primary key((id1, bucket), createdat, id2)
)
with
  clustering ORDER BY (createdat ASC, id2 ASC) AND ...

我有这张 Cassandra 桌子。在多线程环境中,两个线程可以同时向该表插入行。 我有一个要求,表不应该有两行具有相同的(id1bucket)和data 字段具有值null。 这意味着只有表的最后一行(对于每个id1bucket)可以将data 设置为null。 为了在每次插入之前实现这一点,我查询表的最后一行并仅在 data 字段不为空时插入新行。 由于竞争条件,这不起作用。两个线程都检查,获取没有data 的最后一行为空并插入具有null 的行,因此违反了要求。

我认为可以在数据库级别解决此问题。我需要一些首先检查最后一行然后插入新行的事务。在这些动作之间不应插入任何内容。

您能否提示如何在 Cassandra 上实现这一点?

【问题讨论】:

    标签: database multithreading cassandra transactions


    【解决方案1】:

    在 Cassandra 中没有办法实现这一点。正如你已经说过的,你总是会遇到竞争条件。

    除了轻量级事务,Cassandra 没有锁定机制,因为它违背了高速 CRUD 操作的目标。干杯!

    【讨论】:

      【解决方案2】:

      您也许可以让此行为与Lightweight Transaction 一起使用。

      在你的情况下,它可能看起来像:

      INSERT INTO table (id1,bucket,createdat,id2,data)
      VALUES (uuid(),'2021-09-27 13:20',totimestamp(now()),uuid(),'some data')
      IF NOT EXISTS;
      

      基本上,这只会在组合键不存在的情况下执行写入。这个确切的解决方案可能行不通,但它应该为您指明正确的方向。

      【讨论】:

      • 感谢@Aaron,但这不起作用,因为两行有不同的craetedat 字段,IF NOT EXISTS 检查将失败。我需要以某种方式检查是否存在具有相同id1, bucket 但具有data==null 的行。
      猜你喜欢
      • 2018-10-25
      • 2015-05-07
      • 2011-01-24
      • 2016-09-03
      • 2012-08-30
      • 2013-04-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多