繁体   English   中英

获取集合计数而不是JPA Criteria API中的集合?

[英]Get collection count instead of the collection in JPA Criteria API?

可以说我有一个实体:

@Entity
public class Person {

    @Id
    @GeneratedValue
    private Long id;

    @ManyToMany(fetch = FetchType.LAZY)
    private List<Role> roles;

    @ManyToMany(fetch = FetchType.LAZY)
    private List<Permission> permissions;
    // etc
    // other fields here
}

我想要一个使用Criteria API构建查询,该查询可过滤这些用户并显示人员列表以及该实体的其他信息-一个人有多少个角色。

CriteriaBuilder builder = em.getCriteriaBuilder();
CriteriaQuery<Person> query = builder.createQuery(Person.class);
Root<Person> personRoot = query.from(Person.class);
// predicates here

但是,这将我限制为仅返回一个Person实体列表。 我总是可以向实体添加@Transient字段,但这似乎很丑陋,因为我可能有很多不同的查询,并且最终可能会有很多这样的字段。

另一方面-我不能使用HQL并编写查询,因为我要进行复杂的过滤,因此必须处理从HQL查询中添加和删除内容的问题。

我的问题,除了本文标题中的问题之外,是这样的:我如何使用Criteria API查询数据库并返回一个非实体(以防我要过滤Person表但仅返回角色数量,权限等),以及如何针对非常接近实际实体的东西(例如使用角色计数器而不是角色集合的示例)进行处理?

更新使用Hibernate的预测,我想到了这一点。 但是仍然不知道用TODO编写。 Projections.count无法正常工作,因为它需要某种分组方式,而且我似乎无法在Hibernate文档中找到任何示例。

Criteria cr = session.createCriteria(Person.class);

if (id != null) {
    cr.add(Restrictions.eq("id", id));
}

ProjectionList projectionList = Projections.projectionList();
projectionList.add(Projections.property("id"), "id");
projectionList.add(TODO, "rolesCount");

我该如何针对非常接近实际实体的事物执行此操作(例如使用角色计数器而不是角色集合的示例

您可以通过多种方式(例如,使用Hibernate @Forumula属性)为User实体设置这些value属性。 这将在实体加载时发出内联子查询,以在不触及集合的情况下获得计数。

@Formula("select count(*) from roles where user_id = ?")
private int numberOfRoles;

另一个(符合JPA的)选项是通过在数据库级别创建一个视图并将其映射到您的用户来处理这些计算出的字段:

例如

@OneToOne
private UserData userData; //entity mapped to your view (works just like a table)

....

public int getNumberOfRoles(){
   return userData.getRoleCOunt();

要么

通过使用@SecondaryTable联接此用户数据。

CriteriaQuery<Long> query = entityManager.getCriteriaBuilder().get().createQuery(Long.class);
query.select(builder.get().countDistinct(root));

为我工作:)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM