假设我有一份文件
{
maxCountAllowed:100,
currentCount:99
}
我有一个API,用户调用它来增加currentCount,如果它还不是100 ..
if(document.currentCount < document.maxCountAllowed){
document.currentCount ++;
document.save();
}else{
console.log("sorry maximum count reached");
}
假设有2个或更多用户同时调用API ..他们都会发现currentCount
仍然是99,因此函数将继续执行,并且它们都将递增currentCount
是101或更多...我怎么能防止这样的事情?
即使它们都是100,我仍然只希望其中一个能够更新而另一个得到错误信息。
答案 0 :(得分:3)
Mongo提供文档级原子性,如下所述:https://docs.mongodb.com/v3.4/tutorial/update-documents/#behavior这意味着如果对象上有两个并发更新操作,那么它们将连续执行。
此外,更新操作支持$ inc运营商:https://docs.mongodb.com/manual/reference/operator/update/inc/#up._S_inc
最后一部分是$ where where运算符:https://docs.mongodb.com/manual/reference/operator/query/where/#examples请记住,它不像查询常量那样高效。
所以你只能更新符合要求的文件:
db.products.update(
{ $where : "this.currentCount < this.maxCountAllowed" },
{ $inc: { currentCount: 1 } }
);
然后检查操作结果以确定是否有任何更新。
答案 1 :(得分:1)
您可以在数据库上执行此操作作为具有其他查询条件的更新。首先,您必须获取文档以了解限制。然后让我们假设您的文档的_id等于1,因此您可以执行此类更新:
db.yourCollection.update({_id: 1, currentCount: {$lt: 100}}, { $inc: { currentCount: 1 } });
$ inc 将执行增量,但仅当文档的当前状态具有值小于100的currentCount字段时,这是您在本文档的另一个字段中定义的限制。
答案 2 :(得分:1)
我认为你所谈论的案件永远不会发生。想象一下,同时会有2个请求,结果会得到99/100。然后他们都会尝试更新到100/100。您正在递增从节点脚本中的数据库获得的值,而不是直接在mongo中的值。
你也可以使用db.collection.findAndModify
,但看起来没有mongoose API。
https://docs.mongodb.com/manual/reference/method/db.collection.findAndModify/