首页 > 解决方案 > 在 Spring Data JPA 中使用过滤的子元素集合获取父实体列表

问题描述

所以我在这个问题上被困了大约半天,所以我想知道我是否只是把事情复杂化了。

我的应用程序具有三个不同的 Java 对象类:Grandparent、Parent 和 Child。每个祖父母都包含一个父母列表,每个父母都包含一个孩子列表。Child 有一个“isWellBehaved”属性,它是一个布尔值。

我们使用 Spring Data JPA 和 Hibernate 将数据映射到数据库。我们的应用程序包含许多嵌套实体和循环关系,我们依靠投影来减小请求大小。

问题:给定一个祖父母 ID,我想返回所有父母的列表(作为预测)。我希望每个父母都包含一个儿童投影列表,但前提是孩子表现良好。集合中的其余子项应从集合中过滤掉。

实现这一目标的最简单方法是什么?我们目前没有使用Hibernate 过滤器,我也不热衷于引入它们,因为我们不太可能在其他任何地方需要它们(不管怎样,它是否适合这个目的?)。我使用过JPA Criteria API 谓词(很少),但发现很难使其适应这种特定场景。本机查询是要走的路吗?我已经开始朝着这个方向前进,但是由于所有嵌套的依赖关系,在将所有字段映射到我们的 Spring 实体时遇到了一些问题,所以我只想确保在继续之前我什至朝着正确的方向前进。

我的(简化的)父实体类如下所示:

@Entity
@Table(name="parent"
public class Parent {

    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name="parent_id")
    Integer id;

    Integer grandparentId; 

    @OneToMany(mappedBy = "parent")
    List<Child> children;
}

儿童班:

@Entity
@Table(name="child"
public class Child {

    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name="child_id")
    Integer id;

    @ManyToOne
    @JoinColumn(name="parent_id")
    Parent parent;

    boolean isWellBehaved; 
}

父仓库接口:

@RepositoryRestResource(excerptProjection = ParentProjection.class)
public interface ParentRepository extends JpaProjectionRepository<Parent, Integer, ParentProjection> {

    List<ParentProjection> findAllByGrandparent_Id(Integer grandpaId);
}

标签: javaspringhibernatespring-data-jpaprojection

解决方案


您可以在集合上使用 @Where 的 hibernate 注释。它会像

@Entity
@Table(name="parent"
public class Parent {

    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name="parent_id")
    Integer id;

    Integer grandparentId; 

    @Where(clause = "isWellBehaved=true")
    @OneToMany(mappedBy = "parent")
    List<Children> children;
}

推荐阅读