Docs HomeMongoDB Manual

Bulk.find.upsert()

On this page本页内容

Tip

Starting in version 3.2, MongoDB also provides the db.collection.bulkWrite() method for performing bulk write operations.从3.2版本开始,MongoDB还提供了db.collection.bulkWrite()方法来执行批量写入操作。

Description描述

Bulk.find.upsert()

Sets the upsert option to true for an update or a replacement operation and has the following syntax:将更新或替换操作的upsert选项设置为true,并具有以下语法:

Bulk.find(<query>).upsert().update(<update>);
Bulk.find(<query>).upsert().updateOne(<update>);
Bulk.find(<query>).upsert().replaceOne(<replacement>);

With the upsert option set to true, if no matching documents exist for the Bulk.find() condition, then the update or the replacement operation performs an insert. upsert选项设置为true的情况下,如果Bulk.find()条件不存在匹配的文档,则更新或替换操作将执行插入。If a matching document does exist, then the update or replacement operation performs the specified update or replacement.如果确实存在匹配的文档,则更新或替换操作将执行指定的更新或替换。

Use Bulk.find.upsert() with the following write operations:Bulk.find.upsert()与以下写入操作一起使用:

Behavior行为

The following describe the insert behavior of various write operations when used in conjunction with Bulk.find.upsert().以下描述了与Bulk.find.upsert()结合使用时各种写入操作的插入行为。

Insert for Bulk.find.replaceOne()Bulk.find.replaceOne()的插入

The Bulk.find.replaceOne() method accepts, as its parameter, a replacement document that only contains field and value pairs:Bulk.find.replaceOne()方法接受仅包含字段和值对的替换文档作为其参数:

var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { item: "abc123" } ).upsert().replaceOne(
{
item: "abc123",
status: "P",
points: 100,
}
);
bulk.execute();

If the replacement operation with the Bulk.find.upsert() option performs an insert, the inserted document is the replacement document. 如果使用Bulk.find.upsert()选项的替换操作执行插入,则插入的文档就是替换文档。If neither the replacement document nor the query document specifies an _id field, MongoDB adds the _id field:如果替换文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id" : ObjectId("52ded3b398ca567f5c97ac9e"),
"item" : "abc123",
"status" : "P",
"points" : 100
}

Insert for Bulk.find.updateOne()Bulk.find.updateOne()的插入

The Bulk.find.updateOne() method accepts as its parameter either:Bulk.find.updateOne()方法接受以下任一项作为其参数

  • a replacement document that contains only field and value pairs (same as Bulk.find.replaceOne()),仅包含字段和值对的替换文档(与Bulk.find.replaceOne()相同),
  • an update document that contains only update operator expressions, or仅包含更新运算符表达式的更新文档,或
  • an aggregation pipeline (Starting in MongoDB 4.2).一个聚合管道(从MongoDB 4.2开始)。

Field and Value Pairs字段和值对

If the parameter is a replacement document that contains only field and value pairs:如果参数是仅包含字段和值对的替换文档:

var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { status: "P" } ).upsert().updateOne(
{
item: "TBD",
points: 0,
inStock: true,
status: "I"
}
);
bulk.execute();

Then, if the update operation with the Bulk.find.upsert() option performs an insert, the inserted document is the replacement document. 然后,如果使用Bulk.find.upsert()选项的更新操作执行插入,则插入的文档就是替换文档。If neither the replacement document nor the query document specifies an _id field, MongoDB adds the _id field:如果替换文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id" : ObjectId("52ded5a898ca567f5c97ac9f"),
"item" : "TBD",
"points" : 0,
"inStock" : true,
"status" : "I"
}

Update Operator Expressions更新运算符表达式

If the parameter is an update document that contains only update operator expressions:如果参数是仅包含更新运算符表达式的更新文档:

var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { status: "P", item: null } ).upsert().updateOne(
{
$setOnInsert: { qty: 0, inStock: true },
$set: { points: 0 }
}
);
bulk.execute();

Then, if the update operation with the Bulk.find.upsert() option performs an insert, the update operation inserts a document with field and values from the query document of the Bulk.find() method and then applies the specified updates from the update document. 然后,如果使用Bulk.find.upsert()选项的更新操作执行插入,则更新操作将插入一个具有Bulk.find()方法的查询文档中的字段和值的文档,然后应用更新文档中指定的更新。If neither the update document nor the query document specifies an _id field, MongoDB adds the _id field:如果更新文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id" : ObjectId("5e28d1a1500153bc2872dadd"),
"item" : null,
"status" : "P",
"inStock" : true,
"points" : 0,
"qty" : 0
}

Aggregation Pipeline聚合管道

Starting in version 4.2, update methods can accept an aggregation pipeline. For example, the following uses:从4.2版本开始,更新方法可以接受聚合管道。例如,以下使用:

  • the $replaceRoot stage which can provide somewhat similar behavior to a $setOnInsert update operator expression,$replaceRoot阶段可以提供与$setOnInsert更新运算符表达式有些相似的行为,
  • the $set stage which can provide similar behavior to the $set update operator expression,可以提供与$set更新运算符表达式类似的行为的$set阶段,
  • the aggregation variable NOW, which resolves to the current datetime and can provide similar behavior to a $currentDate update operator expression.聚合变量NOW,它解析为当前日期时间,并可以提供与$currentDate更新运算符表达式类似的行为。
var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { item: "Not Found", status: "P" } ).upsert().updateOne(
[
{ $replaceRoot: { newRoot: { $mergeObjects: [ { qty: 0, inStock: true }, "$$ROOT" ] } } },
{ $set: { points: 0, lastModified: "$$NOW" } }
]
);
bulk.execute();

Then, if the update operation with the Bulk.find.upsert() option performs an insert, the update operation inserts a document with field and values from the query document of the Bulk.find() method and then applies the specified aggregation pipeline. 然后,如果使用Bulk.find.upsert()选项的更新操作执行插入,则更新操作将插入一个包含Bulk.find()方法的查询文档中的字段和值的文档,然后应用指定的聚合管道。If neither the update document nor the query document specifies an _id field, MongoDB adds the _id field:如果更新文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id" : ObjectId("5e28cf1e500153bc2872d49f"),
"qty" : 0,
"inStock" : true,
"item" : "Not Found",
"status" : "P",
"points" : 0,
"lastModified" : ISODate("2020-01-22T22:39:26.789Z")
}

Insert for Bulk.find.update()Bulk.find.update()的插入

When using upsert() with the multiple document update method Bulk.find.update(), if no documents match the query condition, the update operation inserts a single document.upsert()与多文档更新方法Bulk.find.update()一起使用时,如果没有文档符合查询条件,则更新操作将插入单个文档。

The Bulk.find.update() method accepts as its parameter either:Bulk.find.update()方法接受以下任一项作为其参数:

  • an update document that contains only update operator expressions, or仅包含更新运算符表达式的更新文档,或
  • an aggregation pipeline (Starting in MongoDB 4.2).一个聚合管道(从MongoDB 4.2开始)。

Update Operator Expressions更新运算符表达式

If the parameter is an update document that contains only update operator expressions:如果参数是仅包含更新运算符表达式的更新文档:

var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { status: "P" } ).upsert().update(
{
$setOnInsert: { qty: 0, inStock: true },
$set: { status: "I", points: "0" }
}
);
bulk.execute();

Then, if the update operation with the Bulk.find.upsert() option performs an insert, the update operation inserts a single document with the fields and values from the query document of the Bulk.find() method and then applies the specified update from the update document. 然后,如果使用Bulk.find.upsert()选项的更新操作执行插入,则更新操作将插入一个包含Bulk.find()方法的查询文档中的字段和值的文档,然后应用更新文档中指定的更新。If neither the update document nor the query document specifies an _id field, MongoDB adds the _id field:如果更新文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id": ObjectId("52ded81a98ca567f5c97aca1"),
"status": "I",
"qty": 0,
"inStock": true,
"points": "0"
}

Aggregation Pipeline聚合管道

Starting in version 4.2, update methods can accept an aggregation pipeline. For example, the following uses:从4.2版本开始更新方法可以接受聚合管道。例如,以下使用:

  • the $replaceRoot stage which can provide somewhat similar behavior to a $setOnInsert update operator expression,$replaceRoot阶段可以提供与$setOnInsert更新运算符表达式有些相似的行为,
  • the $set stage which can provide similar behavior to the $set update operator expression,可以提供与$set更新运算符表达式类似的行为的$set阶段,
  • the aggregation variable NOW, which resolves to the current datetime and can provide similar behavior to the $currentDate update operator expression. 聚合变量NOW,它解析为当前日期时间,并可以提供与$currentDate更新运算符表达式类似的行为。The value of NOW remains the same throughout the pipeline. NOW的值在整个管道中保持不变。To access aggregation variables, prefix the variable with double dollar signs $$ and enclose in quotes.要访问聚合变量,请在变量前面加上双美元符号$$并用引号括起来。
var bulk = db.items.initializeUnorderedBulkOp();
bulk.find( { item: "New Item", status: "P" } ).upsert().update(
[
{ $replaceRoot: { newRoot: { $mergeObjects: [ { qty: 0, inStock: true }, "$$ROOT" ] } } },
{ $set: { points: 0, lastModified: "$$NOW" } }
]
);
bulk.execute();

Then, if the update operation with the Bulk.find.upsert() option performs an insert, the update operation inserts a single document with the fields and values from the query document of the Bulk.find() method and then applies the aggregation pipeline. 然后,如果使用Bulk.find.upsert()选项的更新操作执行插入,则更新操作将插入一个包含Bulk.find()方法的查询文档中的字段和值的文档,然后应用聚合管道。If neither the update document nor the query document specifies an _id field, MongoDB adds the _id field:如果更新文档和查询文档都没有指定_id字段,MongoDB会添加_id字段:

{
"_id" : ObjectId("5e2920a5b4c550aad59d18a1"),
"qty" : 0,
"inStock" : true,
"item" : "New Item",
"status" : "P",
"points" : 0,
"lastModified" : ISODate("2020-01-23T04:27:17.780Z")
}