How to use Querydsl to construct complex predicate that involves multiple tables?

I am trying to utilize Querydsl to fetch some results from a table. So far, this is what I have tried –

Assume there are 5 entities named T1..T5. And I am trying to do this SQL query in Querydsl –

SELECT T1.*
FROM T1,T2,T3,T4,T5
WHERE T1.A=T2.A
AND T2.B=T5.B
AND T4.C=T2.C
AND T1.B=1234;

I tried the following, but the Hibernate query keeps running, and does not seem to end.

booleanBuilder.and(JPAExpressions.select(qT1).from(qT1,qT2,qT3,qT4,qT5)
.where(
    qT1.a.eq(qT2.a)
    .and(qT1.a.eq(qT2.a))
    ... // and so on
    .exists());

I am using the Repository that extends QuerydslPredicateExecutor and using findAll to execute this. The problem is that the query takes forever to run. And I am interested only in the first result that may appear. So, where am I going wrong that is making the query execute forever?

Edit: I opted to use the JPAQuery instead. And of course, the Hibernate query generated is the same. Here is my JPAQuery.

JPQLQuery jpqlQuery = new JPAQuery(entityManager);
        jpqlQuery.select(qT1).from(qT1, qT2, qT3, qT4, qT5).where(booleanBuilder);
        return jpqlQuery.fetch();

How do I incorporate the limit in the above JPAQuery so that only the first result is fetched?

Answer

The complexity is not in the predicate or in QueryDSL, but in the fact that you’re executing it in a subquery that has to be executed for every row in the result. Depending on the total result set size, this may become increasingly difficult to compute. It is however equally complex among QueryDSL, Hibernates HQL, JPA’s JPQL or your databases SQL. So the SQL you’re trying to generate, will be just as slow.

You might succeed at optimising the query using a limit clause. Adding a limit clause to query in QueryDSL is quite trivial: .limit(1). So then your query becomes:

JPQLQuery jpqlQuery = new JPAQuery(entityManager);
        jpqlQuery.select(qT1).from(qT1, qT2, qT3, qT4, qT5).where(booleanBuilder);
        jpqlQuery.limit(1);
        return jpqlQuery.fetch();
Source: stackoverflow
The answers/resolutions are collected from stackoverflow, are licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0 .