为什么在Cassandra数据库中更改页面状态并不总是有效?

时间:2016-07-02 23:53:30

标签: c++ cql3 cassandra-3.0

我有一个相当复杂的Web应用程序,可以在Cassandra数据库中创建HTML页面。

在创建页面时,它会在该页面中保存一个状态,反映出正在处理的事实。

INSERT INTO content (key,                  column1,          value)
             VALUES ('http://domain/path', 'content:status', 0x0201);

(列名来自节俭日......)

当状态为0x0201时,没有其他进程可以对页面执行任何操作。它被视为已锁定

创建页面后,只需一毫秒左右,我将状态切换为"正常"。这是content::status字段的另一个插入。

INSERT INTO content (key,                  column1,          value)
             VALUES ('http://domain/path', 'content:status', 0x0102);

此处状态从0x0201更改为0x0102。仅在我在网站初始化时创建的大约700页中,该状态在22到30个(3%到4%)内没有变化。

这是否会发生,因为第一个INSERT INTO和第二个{{1}}之间的时间太短而Cassandra集群混淆了? (即看到两者一起到达并且它选择其中一个,在这几个失败的情况下恰好是错误的?)

1 个答案:

答案 0 :(得分:0)

当使用C ++驱动程序(以及其他我确定的)时,两个INSERT命令可能最终被发送到两个不同的管道。这是因为驱动程序处理工作线程,并且命令最终可以在任一工作线程管道中完成。

这意味着即使你发送CREATE和更高版本的NORMAL,线程管道也可能最先发送NORMAL然后再发送到Cassandra(即交换数据首次发送到C ++驱动程序的顺序。)然后你最终状态为CREATE ...

这无法直接解决。相反,您可能希望在该页面上工作时使用锁定,一旦完成工作,还要将状态更新为NORMAL,以防其他情况,然后解锁。如果你有一个超时锁定,那么你永远不应该创建一个完整的死锁(即一个进程处理页面A然后是B而没有在处理B之前释放第A页上的锁定,而另一个进程首先处理页面B然后A ... )