写入操作
在此页面上
您可以执行写入操作以插入新文档、更新现有文档、替换现有文档或删除集合中的现有文档。
先决条件
您必须设置以下组件才能运行本指南中的代码示例:
一个
test.restaurants
restaurants.json
集合,其中填充了来自 文档资产Github 中的 文件的文档。以下 import 语句:
import com.mongodb.*; import com.mongodb.client.MongoClients; import com.mongodb.client.MongoClient; import com.mongodb.client.MongoCollection; import com.mongodb.client.MongoDatabase; import com.mongodb.client.model.Filters; import static com.mongodb.client.model.Filters.*; import static com.mongodb.client.model.Updates.*; import com.mongodb.client.model.UpdateOptions; import com.mongodb.client.result.*; import org.bson.Document; import org.bson.types.ObjectId; import java.util.List; import java.util.Arrays; import java.util.ArrayList;
重要
本指南使用Subscriber
实现,如快速入门入门知识中所述。
连接到 MongoDB 部署
首先,连接到 MongoDB 部署,然后声明并定义MongoDatabase
和MongoCollection
实例。
以下代码连接到在端口27017
上的localhost
上运行的独立 MongoDB 部署。 然后,定义database
变量以引用test
数据库,并collection
变量以引用restaurants
集合:
MongoClient mongoClient = MongoClients.create(); MongoDatabase database = mongoClient.getDatabase("test"); MongoCollection<Document> collection = database.getCollection("restaurants");
要了解有关连接到 MongoDB 部署的更多信息,请参阅连接到 MongoDB教程。
插入文档
要将单个文档插入到集合中,可以使用集合的insertOne()
方法:
Document document = new Document("name", "Café Con Leche") .append("contact", new Document("phone", "228-555-0149") .append("email", "cafeconleche@example.com") .append("location",Arrays.asList(-73.92502, 40.8279556))) .append("stars", 3) .append("categories", Arrays.asList("Bakery", "Coffee", "Pastries")); collection.insertOne(document).subscribe(new ObservableSubscriber<Void>());
注意
如果文档中没有指定顶级id
字段,MongoDB 会自动生成一个值并将该字段添加到插入的文档中。
插入多个文档
要插入多个文档,可以使用集合的insertMany()
方法,该方法将要插入的文档列表作为参数。
以下示例将两个文档插入到集合中:
Document doc1 = new Document("name", "Amarcord Pizzeria") .append("contact", new Document("phone", "264-555-0193") .append("email", "amarcord.pizzeria@example.net") .append("location",Arrays.asList(-73.88502, 40.749556))) .append("stars", 2) .append("categories", Arrays.asList("Pizzeria", "Italian", "Pasta")); Document doc2 = new Document("name", "Blue Coffee Bar") .append("contact", new Document("phone", "604-555-0102") .append("email", "bluecoffeebar@example.com") .append("location",Arrays.asList(-73.97902, 40.8479556))) .append("stars", 5) .append("categories", Arrays.asList("Coffee", "Pastries")); List<Document> documents = new ArrayList<Document>(); documents.add(doc1); documents.add(doc2); collection.insertMany(documents).subscribe(new ObservableSubscriber<Void>());;
注意
如果文档中没有指定顶级id
字段,MongoDB 会自动生成一个值并将该字段添加到插入的文档中。
更新现有文档
要更新集合中的现有文档,可以使用集合的updateOne()
或updateMany()
方法。
筛选器
您可以将筛选器文档传递给这些方法,以指定要更新的文档。 筛选器文档规范与读取操作的筛选器文档规范相同。 为了便于创建筛选器对象,驱动程序提供了Filters
辅助类。
要指定空筛选器并匹配集合中的所有文档,请使用空Document
对象作为筛选器。
更新操作符
要更改文档中的字段,MongoDB 提供了更新操作符。 要指定使用更新操作符执行的修改,请创建更新文档。 要了解有关更新操作符的更多信息,请参阅 MongoDB Server手册中的 更新操作符 。
为了便于创建更新文档,驾驶员提供了Updates
辅助类。
重要
id
字段不可变,因此您无法更改文档中id
字段的值。
更新单份文档
即使筛选条件与集合中的多个文档匹配, updateOne()
方法也会更新单个文档。
对restaurants
集合的以下操作会更新id
字段值为ObjectId("57506d62f57802807471dd41")
的文档:
collection.updateOne( eq("_id", new ObjectId("57506d62f57802807471dd41")), combine(set("stars", 1), set("contact.phone", "228-555-9999"), currentDate("lastModified")) ).subscribe(new ObservableSubscriber<UpdateResult>());
具体来说,该操作使用以下方法:
Updates.set()
将stars
字段的值设置为1
,并将contact.phone
字段的值设置为"228-555-9999"
Updates.currentDate()
将lastModified
字段修改为当前日期。 如果lastModified
字段不存在,操作符会将该字段添加到文档中。
更新多个文档
updateMany()
方法会更新所有符合筛选条件的文档。
对restaurants
集合的以下操作会更新stars
字段的值为2
的所有文档:
collection.updateMany( eq("stars", 2), combine(set("stars", 0), currentDate("lastModified")) ).subscribe(new ObservableSubscriber<UpdateResult>());
具体来说,该操作使用以下方法:
Updates.set()
将stars
字段的值设置为0
Updates.currentDate()
将lastModified
字段设置为当前日期。 如果lastModified
字段不存在,操作符会将该字段添加到文档中。
UpdateOptions
使用updateOne()
和updateMany()
方法时,可以包含UpdateOptions
文档来指定upsert
选项或bypassDocumentationValidation
选项:
collection.updateOne( eq("_id", 1), combine(set("name", "Fresh Breads and Tulips"), currentDate("lastModified")), new UpdateOptions().upsert(true).bypassDocumentValidation(true) ).subscribe(new ObservableSubscriber<UpdateResult>());
替换现有文档
要替换集合中的现有文档,可以使用集合的replaceOne()
方法。
重要
id
字段不可变,因此您无法替换文档中的id
字段。
筛选器
您可以将筛选器文档传递给replaceOne()
方法,以指定要替换的文档。 筛选器文档规范与读取操作的筛选器文档规范相同。 为了便于创建筛选器对象,驱动程序提供了Filters
辅助类。
要指定空筛选器并匹配集合中的所有文档,请使用空Document
对象作为筛选器。
即使筛选条件与集合中的多个文档匹配, replaceOne()
方法也最多替换单个文档。
替换文档
要替换文档,请将新文档传递给replaceOne()
方法。
重要
替换文档可以具有与原始文档不同的字段。 在替换文档中,您可以省略id
字段,因为id
字段不可变。 但是,如果您确实包含id
字段,则无法为id
字段指定不同的值。
针对restaurants
集合的以下操作会替换id
字段值为ObjectId("57506d62f57802807471dd41")
的文档:
collection.replaceOne( eq("_id", new ObjectId("57506d62f57802807471dd41")), new Document("name", "Green Salads Buffet") .append("contact", "TBD") .append("categories", Arrays.asList("Salads", "Health Foods", "Buffet")) ).subscribe(new ObservableSubscriber<UpdateResult>());
UpdateOptions
使用replaceOne()
方法时,可以包含UpdateOptions
文档来指定upsert
选项或bypassDocumentationValidation
选项:
collection.replaceOne( eq("name", "Orange Patisserie and Gelateria"), new Document("stars", 5) .append("contact", "TBD") .append("categories", Arrays.asList("Cafe", "Pastries", "Ice Cream")), new UpdateOptions().upsert(true).bypassDocumentValidation(true) ).subscribe(new ObservableSubscriber<UpdateResult>());
Delete Documents
要删除集合中的文档,可以使用deleteOne()
和deleteMany()
方法。
筛选器
您可以将筛选器文档传递给这些方法,以指定要删除的文档。 筛选器文档规范与读取操作的筛选器文档规范相同。 为了便于创建筛选器对象,驱动程序提供了Filters
辅助类。
要指定空筛选器并匹配集合中的所有文档,请使用空Document
对象作为筛选器。
删除单个文档
即使筛选条件与集合中的多个文档匹配, deleteOne()
方法也最多删除单个文档。
对restaurants
集合的以下操作会删除_id
字段值为ObjectId("57506d62f57802807471dd41")
的文档:
collection .deleteOne(eq("_id", new ObjectId("57506d62f57802807471dd41"))) .subscribe(new ObservableSubscriber<DeleteResult>());
删除多个文档
deleteMany()
方法删除所有符合筛选条件的文档。
对restaurants
集合的以下操作将删除stars
字段的值为4
的所有文档:
collection .deleteMany(eq("stars", 4)) .subscribe(new ObservableSubscriber<DeleteResult>());
写关注
写关注描述了从 MongoDB 请求的写入操作确认级别。
您可以在以下级别配置写关注:
在
MongoClient
中通过以下方式:通过创建
MongoClientSettings
实例:MongoClient mongoClient = MongoClients.create(MongoClientSettings.builder() .applyConnectionString(new ConnectionString("mongodb://host1,host2")) .writeConcern(WriteConcern.MAJORITY) .build()); 通过创建
ConnectionString
实例:MongoClient mongoClient = MongoClients.create("mongodb://host1:27017,host2:27017/?w=majority");
在
MongoDatabase
中,使用withWriteConcern()
方法:MongoDatabase database = mongoClient.getDatabase("test").withWriteConcern(WriteConcern.MAJORITY); 在
MongoCollection
中,使用withWriteConcern()
方法:MongoCollection<Document> collection = database .getCollection("restaurants") .withWriteConcern(WriteConcern.MAJORITY);
MongoDatabase
和MongoCollection
实例是不可变的。 在现有MongoDatabase
或MongoCollection
实例上调用withWriteConcern()
会返回一个新实例,并且不会影响调用该方法的实例。
在以下示例中, collWithWriteConcern
实例的写关注为majority
,而collection
的读取偏好不受影响:
MongoCollection<Document> collWithWriteConcern = collection .withWriteConcern(WriteConcern.MAJORITY);
您可以构建MongoClientSettings
、 MongoDatabase
或MongoCollection
实例以包含读关注、读取偏好和写关注的组合。
例如,以下代码在集合级别设置所有三个:
Collection = database.getCollection("restaurants") .withReadPreference(ReadPreference.primary()) .withReadConcern(ReadConcern.MAJORITY) .withWriteConcern(WriteConcern.MAJORITY);