Overview
在本指南中,您可以了解如何使用 Rust 驱动程序执行复合操作。
复合操作将读取和写入操作的功能组合成一个原子动作。 如果您按顺序执行读取操作和写入操作,有人可能会在操作之间更改您的目标文档,从而导致意外结果。 当您执行复合操作时, MongoDB会在您正在修改的文档上放置写锁(write lock),直到操作完成,从而防止中间数据更改。
您可以使用驱动程序执行以下复合操作:
查找并删除一个文档
查找并更新一个文档
查找并替换一个文档
本指南包括以下部分:
示例的样本数据显示复合操作示例使用的样本数据
查找和删除文档描述了如何在单个操作中查找和删除文档
查找和更新文档描述了如何在单个操作中查找和更新文档
查找和替换文档描述了如何在单个操作中查找和替换文档
附加信息提供了本指南中提到的类型和方法的资源和 API 文档链接
提示
要了解如何一次对多个文档执行原子读写操作,请参阅事务指南。
示例样本数据
本指南中的示例使用以下样本文档。 每个文档代表一名学生,并包含有关他们的年龄和就读学校的信息:
{ "name": "Alex Johnson", "age": 8, "school": "Lakeside Elementary" }, { "name": "Samara Khan", "age": 11, "school": "Rolling Hills Middle School" }, { "name": "Ben Joseph", "age": 16, "school": "Aurora High School" }, { "name": "Deanna Porowski", "age": 10, "school": "Lakeside Elementary" }
查找和删除文档
find_one_and_delete()方法查找并删除与指定查询筛选器匹配的第一个文档。 如果文档与筛选条件匹配,该方法将返回Some类型。 如果没有匹配的文档,则返回None类型。
注意
如果要在查找和删除文档之间执行其他操作,可以调用find_one()方法,然后调用delete_one()方法。
修改查找和删除行为
您可以选择通过将选项构建器方法链接到find_one_and_delete()来修改find_one_and_delete()方法的行为。 这些构建器方法设立FindOneAndDeleteOptions结构体字段。
下表描述了FindOneAndDeleteOptions中可用的选项:
选项 | 说明 |
|---|---|
| 查询可运行的最长时间(以毫秒为单位)。 |
| 返回结果时使用的投影。 |
| 返回结果时使用的排序顺序。默认情况下,驱动程序会以自然顺序返回文档,换句说,以文档在数据库中的出现顺序返回。要了解更多信息,请参阅服务器手册词汇表中的自然顺序。 |
| 操作的写关注(write concern)。如果您未设置此选项,则操作会继承为集合设置的写关注(write concern)。要了解有关写关注(write concern)的更多信息,请参阅服务器手册中的写关注(write concern)。 |
| 对结果进行排序时使用的排序规则。要进一步了解排序规则,请参阅排序规则指南。 |
| 用于操作的索引。要了解有关索引的更多信息,请参阅服务器手册中的索引。此选项仅在连接到 MongoDB Server 4.4及更高版本时可用。 |
| 参数和值的映射。您可以在聚合表达式中将这些参数作为变量进行访问。此选项仅在连接到 MongoDB Server 5.0 及更高版本时可用。 |
| 与操作绑定的任意 |
注意
设置选项
您可以通过将选项构建器方法直接链接到 find_one_and_delete() 方法调用来设立FindOneAndDeleteOptions 字段。如果使用的是早期版本的驱动程序,则必须通过将选项构建器方法链接到 builder() 方法来构造 FindOneAndDeleteOptions实例。然后,将选项实例作为参数传递给 find_one_and_delete()。
以下代码展示了如何通过将comment()方法链接到find_one_and_delete()方法来设立comment字段:
let res = my_coll.find_one_and_delete(filter) .comment(bson!("hello")) .await?;
查找和删除示例
以下示例使用find_one_and_delete()方法匹配并删除age字段的值小于或等于10的第一个文档:
let filter = doc! { "age": doc! { "$lte": 10 } }; let res = my_coll.find_one_and_delete(filter).await?; println!("Deleted document:\n{:?}", res);
Deleted document: Some(Document({"_id": ObjectId("..."), "name": String("Deanna Porowski"), "age": Int32(10), "school": String("Lakeside Elementary")}))
查找并更新文档
find_one_and_update()方法查找并更新与指定查询筛选器匹配的第一个文档。 该操作根据您在更新文档中提供的规范来更新文档。 如果文档与筛选条件匹配,该方法将返回Some类型。 如果没有匹配的文档,则返回None类型。
注意
如果要在查找和更新文档之间执行其他操作,可以调用find_one()方法,然后调用update_one()方法。
修改查找和更新行为
您可以选择通过将选项构建器方法链接到find_one_and_update()来修改find_one_and_update()方法的行为。 这些构建器方法设立FindOneAndUpdateOptions结构体字段。
下表描述了FindOneAndUpdateOptions中可用的选项:
选项 | 说明 |
|---|---|
| 指定更新应用的数组元素的过滤器集。要了解更多信息,请参阅 更新文档中的数组指南。 |
| 如果为 |
| 查询可运行的最长时间(以毫秒为单位)。 |
| 返回结果时使用的投影。 |
| 如果 |
| 返回结果时使用的排序顺序。默认情况下,驱动程序会以自然顺序返回文档,换句说,以文档在数据库中的出现顺序返回。要了解更多信息,请参阅服务器手册词汇表中的自然顺序。 |
| 如果为 true,则在没有文档与查询筛选条件匹配时,操作会插入文档。 |
| 操作的写关注(write concern)。如果您未设置此选项,则操作会继承为集合设置的写关注(write concern)。要了解有关写关注(write concern)的更多信息,请参阅服务器手册中的写关注(write concern)。 |
| 对结果进行排序时使用的排序规则。要进一步了解排序规则,请参阅排序规则指南。 |
| 用于操作的索引。要了解有关索引的更多信息,请参阅服务器手册中的索引。此选项仅在连接到 MongoDB Server 4.4及更高版本时可用。 |
| 参数和值的映射。您可以在聚合表达式中将这些参数作为变量进行访问。此选项仅在连接到 MongoDB Server 5.0 及更高版本时可用。 |
| 与操作绑定的任意 |
以下代码展示了如何通过将comment()方法链接到find_one_and_update()方法来设立comment字段:
let res = my_coll.find_one_and_update(filter, update) .comment(bson!("hello")) .await?;
查找和更新示例
此示例演示如何执行以下操作:
调用
find_one_and_update()方法将查询过滤传递给
find_one_and_update(),以匹配school值为"Aurora High School"的文档将更新文档传递给
find_one_and_update(),将school字段设置为"Durango High School",并将age字段递增1将
return_document()方法链接到find_one_and_update()以在更新后返回匹配的文档
let filter = doc! { "school": "Aurora High School" }; let update = doc! { "$set": doc! { "school": "Durango High School" }, "$inc": doc! { "age": 1 } }; let res = my_coll.find_one_and_update(filter, update) .return_document(ReturnDocument::After) .await?; println!("Updated document:\n{:?}", res);
Updated document: Some(Document({"_id": ObjectId("..."), "name": String("Ben Joseph"), "age": Int32(17), "school": String("Durango High School")}))
查找和替换文档
find_one_and_replace()方法查找并替换与指定查询筛选器匹配的第一个文档。 此操作会将文档中除_id字段之外的所有字段替换为您提供的字段和值。 如果文档与筛选条件匹配,该方法将返回Some类型。 如果没有匹配的文档,则返回None类型。
注意
如果要在查找和替换文档之间执行其他操作,可以调用find_one()方法,然后调用replace_one()方法。
修改查找和替换行为
您可以选择通过将选项构建器方法链接到find_one_and_replace()来修改find_one_and_replace()方法的行为。 这些构建器方法设立FindOneAndReplaceOptions结构体字段。
下表描述了FindOneAndReplaceOptions中可用的选项:
选项 | 说明 |
|---|---|
| 如果为 |
| 查询可运行的最长时间(以毫秒为单位)。 |
| 返回结果时使用的投影。 |
| 如果 |
| 返回结果时使用的排序顺序。默认情况下,驱动程序会以自然顺序返回文档,换句说,以文档在数据库中的出现顺序返回。要了解更多信息,请参阅服务器手册词汇表中的自然顺序。 |
| 如果为 true,则在没有文档与查询筛选条件匹配时,操作会插入文档。 |
| 操作的写关注(write concern)。如果您未设置此选项,则操作会继承为集合设置的写关注(write concern)。要了解有关写关注(write concern)的更多信息,请参阅服务器手册中的写关注(write concern)。 |
| 对结果进行排序时使用的排序规则。要进一步了解排序规则,请参阅排序规则指南。 |
| 用于操作的索引。要了解有关索引的更多信息,请参阅服务器手册中的索引。此选项仅在连接到 MongoDB Server 4.4及更高版本时可用。 |
| 参数和值的映射。您可以在聚合表达式中将这些参数作为变量进行访问。此选项仅在连接到 MongoDB Server 5.0 及更高版本时可用。 |
| 与操作绑定的任意 |
以下代码展示了如何通过将comment()方法链接到find_one_and_replace()方法来设立comment字段:
let res = my_coll.find_one_and_replace(filter, replacement) .comment(bson!("hello")) .await?;
查找和替换示例
此示例将执行以下动作:
调用
find_one_and_replace()方法将查询过滤传递给
find_one_and_replace(),以匹配name的值包含string"Johnson"的文档将描述新学生的替换文档传递给
find_one_and_replace()将
return_document()方法链接到find_one_and_replace()以返回替换后的文档将
projection()方法链接到输出中的find_one_and_replace()``to project only the ``name和school字段
let filter = doc! { "name": doc! { "$regex": "Johnson" } }; let replacement = doc! { "name": "Toby Fletcher", "age": 14, "school": "Durango High School" }; let res = my_coll.find_one_and_replace(filter, replacement) .return_document(ReturnDocument::After) .projection(doc! { "name": 1, "school": 1, "_id": 0 }) .await?; println!("Document after replacement:\n{:?}", res);
Document after replacement: Some(Document({"name": String("Toby Fletcher"), "school": String("Durango High School")}))
更多信息
要了解有关本指南中操作的更多信息,请参阅以下文档:
API 文档
要进一步了解本指南所提及的方法和类型,请参阅以下 API 文档: