你可以仅仅删除的$setOnInsert
,因为这将更新操作将被设置为在$inc
运营商指定的值,如果这个文件不存在
https://docs.mongodb.com/v3.2/reference/operator/update/inc/#behavior
如果该字段不存在, $ inc创建该字段并将该字段设置为指定的值。从蒙戈外壳
例子:
> db.dropDatabase()
{ "ok" : 1 }
> db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {upsert: true, returnNewDocument: true})
{ "_id" : "meta", "version" : 1 }
> db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {upsert: true, returnNewDocument: true})
{ "_id" : "meta", "version" : 2 }
> db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {upsert: true, returnNewDocument: true})
{ "_id" : "meta", "version" : 3 }
> db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {upsert: true, returnNewDocument: true})
{ "_id" : "meta", "version" : 4 }
> db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {upsert: true, returnNewDocument: true})
{ "_id" : "meta", "version" : 5 }
如果您需要设置一个给定的版本,第一个初始插件,然后MongoDB中不支持任何运营商原子支持这一点,但后续会安全是一个常见的解决方法:
> db.dropDatabase()
{ "dropped" : "test", "ok" : 1 }
> function updateMeta(){
... function update(){
... return db.test.findOneAndUpdate({_id: "meta"}, { $inc: { version: 1} }, {returnNewDocument: true});
... }
...
... var result = update();
...
... if(result === null){
... db.test.insert({_id: "meta", version: -10});
... result = update();
... }
...
... return result;
... }
>
> updateMeta()
{ "_id" : "meta", "version" : -9 }
> updateMeta()
{ "_id" : "meta", "version" : -8 }
> updateMeta()
{ "_id" : "meta", "version" : -7 }
> updateMeta()
{ "_id" : "meta", "version" : -6 }
> updateMeta()
{ "_id" : "meta", "version" : -5 }
>
我想添加这个例子中,当你有值的嵌套的对象:{_id:1,小时:{0:0,1:0,2:0 }}并且如果文档不存在或只是想要添加并增加一小时如果有的话,增加一小时。其实这是不可能的,也不违反任何逻辑。 – jtomasrl