【问题标题】:Spring Data JPA + JpaSpecificationExecutor + NamedEntityGraphSpring Data JPA + JpaSpecificationExecutor + NamedEntityGraph
【发布时间】:2020-04-17 04:15:12
【问题描述】:

我有两个实体。父母和孩子。

@Entity
public class Parent {

    @Id
    @Column(name = "PARENT_ID")
    private BigInteger id;

    @Column(name = "FIRST_NAME")
    private String firstName;

    @Column(name = "LAST_NAME")
    private String lastName;
}

@Entity
@NamedEntityGraph(name = "Child.parentObj", attributeNodes = @NamedAttributeNodes("parentObj"))
public class Child{
//blah blah blah

@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name="PARENT_ID")
Parent parentObj;

@OneToMany(fetch = FetchType.LAZY)
@JoinColumn(name="CHILD_ID")
Set<Address> address
//blah blah blah
}

ChildRepository.java

public interface ChildRepository extends JpaRepository<T, ID>, JpaSpecificationExecutor<T>{

     @EntityGraph(value="Child.parentObj")
     public List<Child> findAll(Specification<Child> spec);
}

我正在尝试按条件查找子实体,它应该始终有父实体。

我正在尝试在地址表中查找 parentObj 时遇到异常。

Caused by: org.hibernate.QueryException: could not resolve property: parentObj of: com.xxx.Address [..]

我找到了这个链接并尝试了 Joep 给出的解决方案,但同样的错误。

Spring Data JPA + JpaSpecificationExecutor + EntityGraph

我错过了什么。我无法理解为什么/如何限制在子对象中查找 parentObj,因为地址没有对父对象的引用。

我正在按 Address.street 进行搜索。

我也尝试过临时实体图。例外:

org.springframework.dao.InvalidDataAccessApiUsageException: org.hibernate.QueryException: could not resolve property: parentObj of: com.xxx.Address 

Caused by: org.hibernate.QueryException: could not resolve property: parentObj of: com.xxx.Address
    at org.hibernate.persister.entity.AbstractPropertyMapping.propertyException(AbstractPropertyMapping.java:83)
    at org.hibernate.persister.entity.AbstractPropertyMapping.toType(AbstractPropertyMapping.java:77)
    at org.hibernate.persister.entity.AbstractEntityPersister.toType(AbstractEntityPersister.java:1978)
    at org.hibernate.hql.internal.ast.tree.FromElementType.getPropertyType(FromElementType.java:367)
    at org.hibernate.hql.internal.ast.tree.FromElement.getPropertyType(FromElement.java:500)
    at org.hibernate.engine.query.spi.EntityGraphQueryHint.getFromElements(EntityGraphQueryHint.java:95)
    at org.hibernate.engine.query.spi.EntityGraphQueryHint.toFromElements(EntityGraphQueryHint.java:68)
    at org.hibernate.hql.internal.ast.HqlSqlWalker.processQuery(HqlSqlWalker.java:676)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:665)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.collectionFunctionOrSubselect(HqlSqlBaseWalker.java:4905)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.comparisonExpr(HqlSqlBaseWalker.java:4606)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2104)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2029)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2029)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.whereClause(HqlSqlBaseWalker.java:796)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:597)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:301)
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:249)
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:278)
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:206)
    ... 60 more

【问题讨论】:

    标签: spring-data-jpa entitygraph


    【解决方案1】:

    我想通过条件搜索找到子条目并为每个孩子获取 ParentObj。我想加入而不是单独选择父母。我试图通过使用 EntityGraph 来解决这个问题,但它没有用。正如@EKlavya 指出的那样,规范和实体图不能一起工作。

    我解决的方法是:

    root.fetch("parentObj", JOIN.LEFT);
    

    在我的 toPredicate 方法中。这将在 1 个查询中获得具有父级的子实体。

    【讨论】:

      【解决方案2】:

      您使用Child.parentObj 作为实体图名称,但您将实体图命名为Child.parent。使用

      @EntityGraph(value="Child.parent")
      

      没有@NamedEntityGraph

      我们可以定义一个 ad-hoc 实体图,不用 @NamedEntityGraph 直接使用

      @EntityGraph(attributePaths = {"parentObj"})
      

      更新: 实体图和规范都不能一起工作。 有办法解决这个问题。不要急切地让父母先获取孩子,然后从孩子中制作一个孩子ID列表,并让父母使用in子句查询使用孩子ID。总共只需要 2 个查询。如果您想使用 1 个查询来解决此问题,请使用 DSL 进行原始查询。

      【讨论】:

      • parentOBj 出现输入错误。我已经修好了。我也尝试过临时实体图。我无法理解为什么/如何限制在子对象中查找 parentObj,因为地址没有对父对象的引用。
      • 类似错误。堆栈跟踪是不同的。但它正在地址中寻找 parentObj。我从临时实体图开始,然后移至 NamedEntityGraph 以寻求解决方案。
      • 您能否也为即席图添加详细堆栈跟踪
      • 更新了原始帖子的详细信息。感谢您的帮助和时间。
      • 添加完整的堆栈跟踪(不仅仅是 1 行)和父实体类也
      猜你喜欢
      • 2014-12-05
      • 2012-07-15
      • 1970-01-01
      • 1970-01-01
      • 2017-07-17
      • 1970-01-01
      • 2017-11-29
      • 2020-06-16
      • 2020-01-27
      相关资源
      最近更新 更多