Spring MongoRepository 正在更新或更新插入而不是插入

Posted

技术标签:

【中文标题】Spring MongoRepository 正在更新或更新插入而不是插入【英文标题】:Spring MongoRepository is updating or upserting instead of inserting 【发布时间】:2015-05-15 23:30:11 【问题描述】:

我正在使用:

org.springframework.data.mongodb.repository.MongoRepository

我从一个空 DB 开始,并使用 _id = 1234 创建一个对象,例如,将其他一些字符串字段设置为 hello,然后执行:

repository.save(object);

一切正常,它将文档保存在 MondoDB 中。

我创建了一个新对象,设置相同的_id = 1234,但将另一个字符串字段设置为world,然后再保存:

repository.save(newObject);

结果:保存有效,但更新了原始对象。

预期结果:这应该会以 DuplicateKeyException 失败,因为 _id 是唯一的,每次保存时我都使用 2 个单独的对象。

春天的缺陷还是我做错了什么???

【问题讨论】:

【参考方案1】:

Save,根据定义,应该以 upsert 样式更新对象,如果存在则更新,如果不存在则插入。 阅读MongoDb上save操作文档website

mongodb 中的 insert 操作具有您所期望的行为,但从 MongoRepository 文档看来,插入被委托保存,因此不会有任何区别。但是您可以尝试一下,看看它是否适合您。否则,您可以在获取之前检查对象是否存在,因为它是索引查找,它会很快。

编辑:检查您的存储库版本,插入是在 version 1.7 中引入的。

【讨论】:

问题是_id 的行为似乎与任何其他字段不同。例如,如果我在 mongo 文档中有一个名为 name 的字段,并在该字段上创建一个唯一索引,则执行我的问题中提到的步骤将导致预期的 DuplicateKeyException 被抛出。此外,对于 spring mongorepository API,没有insert API,只有save。我觉得这是春天的一个错误。 有一个插入方法:docs.spring.io/spring-data/mongodb/docs/current/api/org/… 索引校验不一样,save中的优化是找到了可以直接更新对象,这是设计的。 啊,我使用的是没有insert API 的旧版本。感谢您指出这一点,我将升级 Spring 并测试 insert 并稍后报告我的结果。非常感谢。 太棒了,我更新了我的 Spring data 和 spring data mongo 版本,现在支持 insert 和 bingo,我得到一个重复的键异常!非常感谢!【参考方案2】:

只有当你有一个字段的 @Id 注释时,应用程序才会更新,经过长时间的困难发现这个

@Document(collection="bus")
public class Bus 

//  @Indexed(unique=true, direction=IndexDirection.DESCENDING, dropDups=true)
    @Id
    private String busTitle; 
    private int totalNoOfSeats;
    private int noOfSeatsAvailable; 
    private String busType; 

但不知何故我无法使用 @Indexed(unique=true, direction=IndexDirection.DESCENDING, dropDups=true)

【讨论】:

不要和我一样混淆org.springframework.data.annotation.Idjavax.persistence.Id,应该用第一个!

以上是关于Spring MongoRepository 正在更新或更新插入而不是插入的主要内容,如果未能解决你的问题,请参考以下文章

使用 Spring Data MongoRepository 进行更新查询的自定义方法

Spring MongoRepository,在哪里捕获异常?

Spring Data 的 MongoTemplate 和 MongoRepository 有啥区别?

如何在使用带有 Spring 数据的 MongoRepository 的查询注释时显示查询

使用Spring Data Mongodb的MongoRepository类进行增删改查

如何防止某些 HTTP 方法从我的 MongoRepository 中导出?