Unikanie n + 1 gorliwego pobierania skojarzeń elementów kolekcji dziecka

Mam następujące klasy:

@Entity
@Table(name = "base")
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "DISCRIMINATOR", discriminatorType = DiscriminatorType.STRING)
@ForceDiscriminator
public class Base {
    // ...
}

@Entity
@DiscriminatorValue("foo")
public class Foo extends Base {
    @OneToMany( mappedBy = "foo", cascade=CascadeType.ALL )
    private List<Bar> bars = new ArrayList<Bar>();

    // ...
}

@Entity
public class Bar {
    @ManyToOne (optional = false)
    @JoinColumn(name = "foo_id" )
    private Foo foo;

    @OneToOne
    @JoinColumn(name = "baz_id", nullable = false)
    private Baz baz;

    //...
}

@Entity
public class Baz {
    // ...
}

Teraz zasadniczo chcę załadować wszystkoBase, ale chętnie słupki obciążenia, jeśli mają zastosowanie, więc używam następującego zapytania:

SELECT b FROM Base b LEFT JOIN FETCH b.bars

Chociaż to działa, wydaje się, że generuje problem SELECT N + 1 dla elementów paska:

Hibernate: /* SELECT b FROM Base b LEFT JOIN FETCH b.bars */ SELECT ...
Hibernate: /* load com.company.domain.Baz */ SELECT ...
Hibernate: /* load com.company.domain.Baz */ SELECT ...

Czy można powiedzieć hibernacji, aby chętnie wczytał skojarzenie dla każdego elementu w kolekcji potomnej bez uciekania się do N + 1 SELECT?

Próbowałem czegoś podobnego do następującego zapytania, które oczywiście nie działa, ponieważ jego kolekcja:

SELECT b FROM Base b LEFT JOIN FETCH b.bars LEFT JOIN FETCH b.bars.baz
//Results in: illegal attempt to dereference collection [Foo.id.bars] with element property reference [baz]

Próbowałem też użyćIN(b.bars) barsi chociaż pozwala mi to odwoływać się do kolekcji podrzędnej, nie wydaje się, że chętnie ładuje kolekcję pasków, która jest moim celem.

Wyjaśnienie, dlaczego tak się dzieje, byłoby również miłe, ponieważ nie mogę tego zrozumieć.

questionAnswers(3)

yourAnswerToTheQuestion