简体   繁体   English

如何使用 CriteriaBuilder 加入选择

[英]How to use CriteriaBuilder to join on selection

How to join a table with a selection using CriteriaBuilder?如何使用 CriteriaBuilder 连接带有选择的表?

Suppose I have this query:假设我有这个查询:

SELECT 
    tbl1.*, 
    tbl2.total 
FROM 
    table_1 tbl1 
LEFT JOIN 
    (SELECT col_id AS id, SUM(value) AS total FROM table_2 WHERE active = 1 GROUP BY col_id) tbl2 
ON 
    tbl1.id = tbl2.id;

Where the definition of table_1 is:其中 table_1 的定义是:

CREATE TABLE table_1(
    id NUMBER(19, 0),
    -- other columns
)

... and table_2 ... ... 和 table_2 ...

CREATE TABLE table_2(
    id NUMBER(19, 0),
    col_id NUMBER(19, 0),
    value NUMBER(14, 2),

    -- other columns
    FOREING KEY (col_id) REFERENCES table_1(id);
)

This is not possible with plain JPA or Hibernate.这对于普通的 JPA 或 Hibernate 是不可能的。 With Hibernate you can model this query if the subquery is static, but for dynamic subqueries you will need something like Blaze-Persistence which works on top of JPA/Hibernate and provides support for these things.如果子查询是静态的,您可以使用 Hibernate 对这个查询进行建模,但是对于动态子查询,您将需要类似 Blaze-Persistence 的东西,它在 JPA/Hibernate 之上工作并为这些东西提供支持。

For the static query solution you can do this:对于静态查询解决方案,您可以这样做:

@Entity
@Table(name = "table1")
public class Table1 {
  @Column(name = "id")
  private Integer id;
  @ManyToOne(fetch = FetchType.LAZY)
  @JoinColumn(name = "id", insertable = false, updatable = false)
  private Table2 table2;
}

@Entity
@Subselect("SELECT col_id AS id, SUM(value) AS total FROM table_2 WHERE active = 1 GROUP BY col_id")
public class Table2Query {
  @Column(name = "id")
  private Integer id;
  @Column(name = "total")
  private BigDecimal total;
}

Here is a nice article by Vlad Mihalcea about Blaze-Persistence if you want a dynamic solution ie where the query structure isn't fixed: https://vladmihalcea.com/blaze-persistence-jpa-criteria-queries/如果您想要一个动态解决方案,即查询结构不固定,这是 Vlad Mihalcea 关于 Blaze-Persistence 的一篇不错的文章: https : //vladmihalcea.com/blaze-persistence-jpa-criteria-queries/

Use the join method in root and use it to get the values from the other table.在 root 中使用 join 方法并使用它从另一个表中获取值。 Note: you need to add the relation in the entity depending on the relationship of these tables (onetone, manytoone or onetomany).注意:您需要根据这些表的关系(onetone、manytoone 或 onetomany)在实体中添加关系。 Something like this:像这样的东西:

Entity code Table1:实体代码表1:

@OneToOne
private Table2 table2;

Search code example:搜索代码示例:

(Root<Table1> root, CriteriaQuery<?> query, CriteriaBuilder cb) -> {
           Join<Table1, Table2> joinTable2 = root.join("table2");
           cb.equal(joinTable2.get("active"), 1);
           .. other filters ..
};

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

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