基于cassandra轻量级事务的序列生成器一致性失败?

nzk0hqpo  于 2021-06-13  发布在  Cassandra
关注(0)|答案(1)|浏览(405)

总结
我们的团队继承了这个使用cassandra实现的序列生成器;
table

CREATE TABLE IF NOT EXISTS sequences (
  id_name varchar,
  next_id bigint,
  instance_name varchar,
  PRIMARY KEY (id_name)
)WITH COMPRESSION = { ... };
GET_LOCK("UPDATE sequences USING TTL 10 set instance_name = ?  where id_name = ? IF instance_name = null", ConsistencyLevel.LOCAL_QUORUM), 

SELECT_SEQUENCE("SELECT next_id from sequences where id_name = ?",
            ConsistencyLevel.LOCAL_QUORUM)

UPDATE_SEQUENCE("UPDATE sequences SET next_id= ? where id_name= ? IF next_id= ?",ConsistencyLevel.LOCAL_QUORUM), 

REMOVE_LOCK("UPDATE sequences set instance_name = null where id_name = ? IF instance_name = ?", ConsistencyLevel.LOCAL_QUORUM);

(note: ConsistencyLevel was set to LOCAL_SERIAL in Java)

它一直运行良好,直到昨天,我们发现两个不同的java应用程序节点具有相同的序列号
事情发生的时间戳

AppNode 1

getlock:           4:25:14.480 
UpdateSequence:    4:25:14.486 

AppNode 2

getlock:           4:25:14,489
UpdateSequence:    4:25:14,496

怎么会这样?我们怎样才能知道到底发生了什么?

kxeu7u2r

kxeu7u2r1#

可能发生的情况 next_id 如果 instance_name 过期原因 TTL ```

SELECT_SEQUENCE("SELECT next_id from sequences where id_name = ?",
ConsistencyLevel.LOCAL_QUORUM)

现在假设下面的操作序列 `instanceOne` 设置锁---->
instance_name=instanceOne `instanceOne` 阅读 `next_id` 值---->
next_id=value1 `instanceOne` 有问题,没打电话 `UPDATE_SEQUENCE` 持续10秒
10秒过去了---->
instance_name=null `instanceTwo` 设置锁->
instance_name=instanceTwo `instanceOne` 读起来是一样的 `next_id` 价值-> `next_id=value1` 两个示例都尝试更新 `next_id` 具有相同的下一个值。但基于这一点的价值观 `instanceTwo` 成功了,对于 `instanceOne` 两个示例都尝试通过移除 `instance_name` 但是基于这一点的价值观 `instanceTwo` 成功了,对于 `instanceOne` 不确定行动的时间戳。
一个问题是它们如何成功地与相同的值关联
如果日志来自应用程序,那么它可以表示 `query attempted time` 而不是 `query execution time in Cassandra` 

相关问题