java - Spring Data Mongodb 存储库没有正确实现继承

标签 java spring spring-data spring-data-mongodb

有两种类型的实体,映射到单个 MongoDB 集合中的两个 Java 类:

@Document
public class Superclass { ... }

@Document(collection = "superclass")
public class Subclass extends Superclass { ... }

以及这些实体的两个存储库:

public interface SuperclassRepository extends MongoRepository<Superclass, String> {}
public interface SubclassRepository extends MongoRepository<Subclass, String> {}

MongoRepositories 没有正确处理实体的继承。在查询所有 Subclass 对象(例如 SubclassRepository.findAll())时,结果集包含 Superclass 对象,这些对象已实例化(或至少已实例化)已尝试实例化),对于属于 Subclass 但不属于 Superclass 的字段具有 null 值。

预期的结果是 SubclassRepository 应该只返回 Subclass 对象,而 SuperclassRepository 应该返回 Superclass子类 对象。它在 Spring Data JPA 中以这种方式工作。

有没有人遇到过这个错误并有解决方法?

最佳答案

我遇到了同样的问题。

查看源代码,令我惊讶的是它并没有实现。它添加了 Collection 名称和实体类,但没有在最终查询中插入 _class 属性。 在查看它之后,我意识到 Mongo 如何知道从 SuperClass 派生的 SubClass1 或 Subclass2。 所以我只是重写 SimpleMongoRepository 类并创建我自己的工厂来放置该类而不是默认的 SimpleMongoRepository

这里是我添加的:

public MySimpleMongoRepository(MongoEntityInformation<T, ID> metadata, MongoOperations mongoOperations) {

    Assert.notNull(mongoOperations);
    Assert.notNull(metadata);

    this.entityInformation = metadata;
    this.mongoOperations = mongoOperations;
    Reflections reflections = new Reflections("com.cre8techlabs.entity");
    Set<String> subTypes = reflections.getSubTypesOf(entityInformation.getJavaType()).stream().map(Class::getName).collect(Collectors.toSet());
    subTypes.add(entityInformation.getJavaType().getName());
    this.baseClassQuery = Criteria.where("_class").in(subTypes.toArray());
}

这里是一个查找实现的例子

public T findOne(ID id) {
    Assert.notNull(id, "The given id must not be null!");
    Query q = getIdQuery(id).addCriteria(baseClassQuery);

    return mongoOperations.findOne(q, entityInformation.getJavaType(), entityInformation.getCollectionName());
}

对我有用,就是怕时间长一点

关于java - Spring Data Mongodb 存储库没有正确实现继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28025710/

相关文章:

spring-data - 使用 Spring Data MongoDB Reactive 进行批量更新

java - Spring 数据自定义 N1QL 查询将属性文档返回为 null

java - 通过 Docker 在 Tomcat 上部署 .war - 404

Spring + Hibernate 如何防止回滚

java - 代码似乎处于无限循环中,无法识别位置

spring - 如何使用 Spring MVC 3.1 获取引用 URL

security - Grails + Spring Security一次登录

json - 所有对象的单个自定义反序列化器作为它们的 ID 或在 POST/PUT 期间嵌入整个对象

Java正则表达式。获取某些关键字之间的子字符串

java - 从不同的类调用 jdbc 连接获取 "java.lang.ClassNotFoundException: oracle.jdbc.driver.OracleDriver"