Spring Data MongoDB 中替换整个文档最直接的方法是通过其 id 使用 save() 方法,findAndReplace() 提供了一个替代方法,允许通过一个简单的查询来确定要替换的文档。
通过使用 findAndReplace() 方法替换符合条件的文档,代码如下:
package com.hxstrive.springdata.mongodb;
import com.hxstrive.springdata.mongodb.entity.Person;
import com.hxstrive.springdata.mongodb.entity.Worker;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.mongodb.core.FindAndReplaceOptions;
import org.springframework.data.mongodb.core.MongoTemplate;
import java.util.Arrays;
import java.util.Optional;
import static org.springframework.data.mongodb.core.query.Criteria.where;
import static org.springframework.data.mongodb.core.query.Query.query;
@SpringBootTest
class FindAndReplaceTest {
   @Autowired
   private MongoTemplate mongoTemplate;
   @Test
   void contextLoads() {
       // 删除集合
       mongoTemplate.dropCollection(Worker.class);
       // 准备数据
       // 插入三个工人数据,以及本年度前四个月的薪水
       mongoTemplate.insert(Worker.builder().name("Tom").age(30)
               .salarys(Arrays.asList(7000f, 6900f, 7200f, 8100f)).build());
       // 将 name 为 “Tom” 的文档替换成 name=Tom-new, age=29
       Optional<Person> result = mongoTemplate.update(Worker.class)
               // 1、创建查询条件,查询 name 等于 Tom 等文档
               .matching(query(where("name").is("Tom")))
               // 2、创建要替换的对象
               .replaceWith(Worker.builder().name("Tom-new").age(29).build())
               // 3、设置附加信息,如:upsert、returnNew 返回新数据
               .withOptions(FindAndReplaceOptions.options().upsert().returnNew())
               // 4、将结果映射为 Person 类型,如果没有指定,则使用初始域类型 Worker
               .as(Person.class)
               // 5、触发实际处理
               .findAndReplace();
       // 获取最新结果
       Person person = result.get();
       System.out.println(person);
   }
}运行代码,输出如下:
Person(id=63ad2796f67ade4b7b940fbe, name=Tom-new, age=29)
请注意,被替换的文档本身不能持有 ID,因为现有文档的 ID 将由存储本身携带到被替换的文档中。还要记住,findAndReplace() 方法只会根据给定的排序顺序替换第一个匹配查询条件的文档。
