Ответ
Ленивая загрузка (Lazy Loading) в Hibernate — это стратегия отложенной загрузки связанных сущностей или коллекций. Данные загружаются не сразу при получении родительского объекта, а только при первом прямом обращении к ним. Это стандартный и рекомендуемый подход для оптимизации производительности.
Как работает:
При загрузке сущности Hibernate возвращает прокси-объект для связанных полей с FetchType.LAZY. Реальный SQL-запрос к базе данных выполняется в момент первого вызова метода геттера этого поля.
Пример настройки:
@Entity
public class Order {
@Id
private Long id;
// Коллекция загрузится только при вызове getItems()
@OneToMany(fetch = FetchType.LAZY, mappedBy = "order")
private List<OrderItem> items;
// ...
}
Ключевая проблема — LazyInitializationException: Исключение возникает при попытке доступа к ленивой коллекции вне контекста открытой сессии (Session) или транзакции. Прокси не может выполнить запрос к БД.
Способы решения (загрузки данных до закрытия сессии):
- JOIN FETCH в HQL/JPQL:
SELECT o FROM Order o JOIN FETCH o.items WHERE o.id = :id - Использование EntityGraph.
- Вызов
Hibernate.initialize(proxy)внутри сессии.
По умолчанию: @OneToMany и @ManyToMany — LAZY, @ManyToOne и @OneToOne — EAGER (но для @OneToOne с optional=false тоже EAGER). Рекомендуется везде использовать LAZY и загружать связи явно, когда они нужны.