2

想象一下这样的查询:

match (i:QuestionOrder) 
set i.count=i.count+1 
merge (q:Question {text: '+text here+', index: i.count}) 
return q

如果集合发生在同一事务中,Neo4j 保证写锁,这由 node-neo4j 中的同一查询暗示。但是,我得到以下输出:

[
  {
    "columns":["q"],
    "data":[{"text":"Have Kids...","index":1,"_id":542}]
  },
  {
    "columns":["q"],
    "data":[{"text":"You are...","index":1,"_id":545}]
  }
]

据我了解,锁应该防止index相同。我在这里错过了什么吗?我该如何解决这个问题?

4

1 回答 1

0

更改此查询以添加额外的测试可能有助于并发工作。如果您有两个并发事务,则在设置操作时获取锁。所以两者都已经读取了 i.count 并且正在等待相同的值。

所以要么你早点抓住那个锁:

match (i:QuestionOrder) 
set i.lock = NOT i.lock
set i.count=i.count+1 
merge (q:Question {text: '+text here+', index: i.count}) 
return q

或者你添加一个额外的检查来避免合并发生(然后你必须重试)

match (i:QuestionOrder) 
WITH i, i.count + 1 as new_count
set i.count = new_count
WITH i, new_count
WHERE i.count = new_count
merge (q:Question {text: '+text here+', index: i.count}) 
return q

或者在同一个 tx 中发送两个不同的语句,其中第一个执行锁定。

于 2015-08-08T17:54:28.150 回答