2015-12-02 24 views
6

我正在嘗試在QueryDSL中編寫查詢以獲取按其parentId分組的表中最早的元素。QueryDSL和具有元組條件的子查詢

的SQL當量應該是:

SELECT a.* FROM child a 
    INNER JOIN 
    (
     SELECT parentId, MAX(revision) FROM child GROUP BY parentId 
    ) b 
    ON ( 
     a.parentId = b.parentId AND a.revision = b.revision 
    ) 

現在QueryDSL我卡的語法。

JPQLQuery<Tuple> subquery = JPAExpressions 
       .select(child.parent, child.revision.max()) 
       .from(child) 
       .groupBy(child.parent); 

HibernateQuery<Child> query = new HibernateQuery<>(session); 
query.from(child) 
    .where(child.parent.eq(subquery.???).and(child.revision.eq(subquery.???)))); 

如何使用子查詢編寫此查詢?

中的表看起來像這樣:

___parent___ (not used in this query, but exists) 
parentId 
P1  | * 
P2  | * 
P3  | * 

___child___ 
parentId | revision 
P1  | 1  | * 
P1  | 2  | * 
P1  | 3  | * 
P2  | 2  | * 
P2  | 3  | * 
P3  | 1  | * 

___result from child, the highest revision for each parentId___ 
P1  | 3  | * 
P2  | 3  | * 
P3  | 1  | *

我試過到目前爲止:

.where(JPAExpressions.select(child.parent,child.revision).eq(subquery)); 

-> org.hibernate.hql.internal.ast.QuerySyntaxException: unexpected end of subtree 

和許多語法錯誤......

我用一個髒循環,現在,因爲我還沒有找到解決方案。

+0

子表中是否有唯一鍵? –

+0

是的,child.id和parent.parentId是各自的主鍵。 (非常感謝您花時間回答:)) –

回答

1

在JPA子查詢中只能出現在where部分。

這裏是您查詢

select(child).from(child).where(child.revision.eq(
    select(child2.revision.max()) 
.from(child2) 
.where(child2.parent.eq(child.parent)) 
.groupBy(child2.parent))).fetch() 
+0

感謝您的回答。當修訂號碼相同時,此查詢不起作用。 Child.revision不是唯一的。在我的查詢中沒有「child2」,只有父母及其子女。這就是爲什麼我需要匹配元組,ParentId和修訂版的查詢 –

+0

的加入部分的值都是好的,是在父級範圍內唯一的子版本?如果沒有,那麼這將返回確實返回每父母多行。 –

+0

我在問題中添加了一個數據示例。 –

1

我帶你可以使用Expressions.list()在子句中指定多個列:

query.from(child).where(Expressions.list(child.parent, child.revision).in(subquery)); 

另一種方法是使用innerJoin(),如您原始SQL。