Scenario
There is still the same problem but we solve it with a different query.
Solution
With join fetch we can tell Hibernate to load associations immediately. Hibernate will use a single SQL select which joins the chapters to the book table.
List<Book> books = session.createQuery( "select b from Book b left join fetch b.chapters where b.name like ?") .setString(0, "Java%") .setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY).list();
The same with a criteria query:
List<Book> books = session.createCriteria(Book.class) .setFetchMode("chapters", org.hibernate.FetchMode.JOIN) .add(Restrictions.like("name", "Java", MatchMode.START)) .setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY).list();
The performance is very good but we must be aware that we will load all chapters into memory. Finally, don’t use join fetch with multiple collections, you will create a rapidly growing Cartesian product. A join will combine all possible combinations. Let’s do a SQL join on data where every book have two chapters and two comments.
select * from book b left join chapters c on b.id=c.book_id left join comment cm on b.id=cm.book_id
Book id | Other book columns | Chapter id | Other chapter columns | Comment id | Other comment columns |
---|---|---|---|---|---|
1 | … | 2 | … | 2 | … |
1 | … | 1 | … | 1 | … |
1 | … | 1 | … | 2 | … |
1 | … | 2 | … | 1 | … |