文档菜单
文档首页
/ / /
Java反应式流驱动程序

POJO CRUD 操作示例

本页内容

  • 先决条件
  • 创建自定义 CodecRegistry
  • 使用 CodecRegistry
  • 将 POJO 插入 MongoDB
  • 插入 Person 实例
  • 插入多个 Person 实例
  • 查询集合
  • 指定查询过滤器
  • 获取匹配过滤器的单个 Person
  • 获取所有匹配过滤器的 Person 实例
  • 更新文档
  • 更新单个 Person
  • 更新多个 Person 实例
  • 替换单个 Person
  • 删除文档
  • 删除匹配过滤器的单个 Person
  • 删除所有匹配过滤器的 Person 实例

本指南使用普通的 Java 对象(POJO),而不是通用的Document 类来建模文档。

本指南中的代码示例来自PojoQuickTour.java 文件在驱动源代码 GitHub 仓库中。

重要

本指南使用自定义 Subscriber 实现,这些实现已在示例自定义 Subscriber 实现 指南中描述。

您必须设置以下组件才能运行本指南中的代码示例

  • MongoDB 服务器在 MongoDB 默认端口(27017)上运行

  • 在项目中安装了驱动依赖项

  • 以下导入语句

    import com.mongodb.client.result.InsertOneResult;
    import com.mongodb.client.result.InsertManyResult;
    import com.mongodb.client.result.DeleteResult;
    import com.mongodb.client.result.UpdateResult;
    import com.mongodb.reactivestreams.client.MongoClient;
    import com.mongodb.reactivestreams.client.MongoClients;
    import com.mongodb.reactivestreams.client.MongoCollection;
    import com.mongodb.reactivestreams.client.MongoDatabase;
    import org.bson.codecs.configuration.CodecRegistry;
    import org.bson.codecs.pojo.PojoCodecProvider;
    import java.util.List;
    import static com.mongodb.client.model.Filters.*;
    import static com.mongodb.client.model.Updates.*;
    import static java.util.Arrays.asList;
    import static org.bson.codecs.configuration.CodecRegistries.fromProviders;
    import static org.bson.codecs.configuration.CodecRegistries.fromRegistries;
  • POJO 类定义。从 GitHub 上驱动源代码仓库复制 PersonAddress POJO 的完整代码

在您可以使用POJO与驱动程序一起使用之前,您需要配置CodecRegistry以包含处理POJOs到和从BSON的编解码器。完成此操作的最简单方法是使用PojoCodecProvider.builder()方法创建和配置一个CodecProvider

以下示例结合了默认编解码器注册表和配置为自动创建POJO Codec实例的PojoCodecProvider

CodecRegistry pojoCodecRegistry = fromRegistries(
MongoClientSettings.getDefaultCodecRegistry(),
fromProviders(PojoCodecProvider.builder().automatic(true).build())
);

注意

将按顺序检查注册表,直到其中一个返回所需类的编解码器。应将DefaultCodecRegistry放在列表中第一,而PojoCodecProvider应始终是最后一个CodecProvider,因为它几乎可以为任何类提供编解码器。

以下列表描述了设置pojoCodecRegistry以使用的方法

  • 在实例化MongoClient对象时设置它

    MongoClientSettings settings = MongoClientSettings.builder()
    .codecRegistry(pojoCodecRegistry)
    .build();
    MongoClient mongoClient = MongoClients.create(settings);
  • 使用一个替代的CodecRegistryMongoDatabase

    database = database.withCodecRegistry(pojoCodecRegistry);
  • 使用一个替代的CodecRegistryMongoCollection

    collection = collection.withCodecRegistry(pojoCodecRegistry);

编解码器注册表会自动尝试为未知类创建POJO Codec。这允许您开箱即用使用POJO,而无需任何额外配置。

在您可以将POJO插入MongoDB之前,创建一个配置了POJO类的MongoCollection实例。

MongoCollection<Person> collection = database.getCollection("people", Person.class);

要将人员插入集合中,请使用集合的insertOne()方法

Person ada = new Person("Ada Byron", 20, new Address("St James Square", "London", "W1"));
collection.insertOne(ada).subscribe(new OperationSubscriber<InsertOneResult>());

要插入多个Person实例,可以使用集合的insertMany()方法,该方法需要一个包含Person实例的列表作为参数。

以下示例将多个Person实例添加到集合中

List<Person> people = asList(
new Person("Charles Babbage", 45, new Address("5 Devonshire Street", "London", "W11")),
new Person("Alan Turing", 28, new Address("Bletchley Hall", "Bletchley Park", "MK12")),
new Person("Timothy Berners-Lee", 61, new Address("Colehill", "Wimborne", null))
);
collection.insertMany(people).subscribe(new OperationSubscriber<InsertManyResult>());

要查询集合,可以使用find()方法。

以下示例将打印集合中所有的Person实例

collection.find().subscribe(new PrintToStringSubscriber<>());
Person{id='...', name='Ada Byron', age=20, address=Address{street='St James Square', city='London', zip='W1'}}
Person{id='...', name='Charles Babbage', age=45, address=Address{street='5 Devonshire Street', city='London', zip='W11'}}
Person{id='...', name='Alan Turing', age=28, address=Address{street='Bletchley Hall', city='Bletchley Park', zip='MK12'}}
Person{id='...', name='Timothy Berners-Lee', age=61, address=Address{street='Colehill', city='Wimborne', zip='null'}}

为了查询符合特定条件的Person实例,将一个过滤器对象传递给find()方法。为了便于创建过滤器对象,驱动器提供了Filters辅助方法。

重要

在查询POJO时,您必须针对文档字段名进行查询,而不是POJO属性名。它们默认相同,但可以更改POJO属性名映射的方式。

以下示例通过传递一个指定等量条件的eq()过滤器对象来查找数据库中第一个具有address.city值为WimbornePerson

collection.find(eq("address.city", "Wimborne"))
.first()
.subscribe(new PrintToStringSubscriber<>());
Person{id='591dbc2550852fa685b3ad1a', name='Timothy Berners-Lee', age=61, address=Address{street='Colehill', city='Wimborne', zip='null'}}

以下示例打印出所有age值大于30的文档。

collection.find(gt("age", 30)).subscribe(new PrintToStringSubscriber<>());

要更新集合中的文档,您可以使用集合的 updateOne()updateMany() 方法。

将以下参数传递给方法

  • 过滤器对象,用于确定要更新的文档或文档。要指定空过滤器并匹配所有 Person 实例,请使用空的 Document 对象。

  • 指定要修改的文档的更新文档。要查看可用的操作符列表,请参阅服务器手册中的更新操作符

更新方法返回一个 UpdateResult 类型,该类型提供了有关操作的信息,包括更新的文档数量。

要更新单个 Person,请使用 updateOne() 方法。

以下示例将名为 "Ada Byron"Person 的年龄更新为 23,并将其姓名更新为 "Ada Lovelace"

collection.updateOne(
eq("name", "Ada Byron"),
combine(set("age", 23), set("name", "Ada Lovelace"))
).subscribe(new OperationSubscriber<>());

要更新所有符合筛选条件的 Person 实例,请使用 updateMany() 方法。

以下示例将所有具有 zip 值的文档的 zip 字段设置为 null

collection.updateMany(not(eq("zip", null)), set("zip", null))
.subscribe(new OperationSubscriber<>());

另一种更改现有 Person 实例的方法是使用 replaceOne() 方法。

以下示例使用前面 insertOne 示例 中引用的 ada 变量替换名为 "Ada Lovelace"Person

collection.replaceOne(eq("name", "Ada Lovelace"), ada)
.subscribe(new OperationSubscriber<>());

要从集合中删除文档,您可以使用集合的 deleteOne()deleteMany() 方法。

传递一个筛选对象以匹配要删除的文档或文档。要指定空筛选,请使用空 Document 对象。

删除方法返回一个 DeleteResult 类型,它提供有关操作的信息,包括删除的文档数量。

要删除与过滤器匹配的单个 Person,请使用 deleteOne() 方法。

以下示例删除了一个地址城市值为 WimbornePerson

collection.deleteOne(eq("address.city", "Wimborne"))
.subscribe(new OperationSubscriber<>());

要删除与过滤器匹配的多个 Person 实例,请使用 deleteMany() 方法。

以下示例删除了所有地址城市值为 LondonPerson 实例。

collection.deleteMany(eq("address.city", "London"))
.subscribe(new OperationSubscriber<>());

返回

验证驱动程序签名