Як працює механізм flush в Hibernate
Flush — процес синхронізації даних з persistence context (кеш Hibernate) в базу даних. Розуміння механізму flush критично важливе для управління транзакціями та оптимізації прод...
Огляд
Flush — процес синхронізації даних з persistence context (кеш Hibernate) в базу даних. Розуміння механізму flush критично важливе для управління транзакціями та оптимізації продуктивності.
🟢 Junior Level
Що таке flush
Flush — це процес запису всіх змін з пам’яті (persistence context) в базу даних.
User user = entityManager.find(User.class, 1L);
user.setName("New Name"); // змінено в пам'яті
// Flush ще не відбувся — БД НЕ оновлена!
entityManager.flush(); // явний flush — UPDATE виконано в БД
// або
// При commit — автоматичний flush
Коли відбувається flush
- При
commitтранзакції — автоматично - При
entityManager.flush()— явно - Перед виконанням запиту — щоб повернути актуальні дані
🟡 Middle Level
FlushMode
// AUTO (за замовчуванням) — flush при необхідності
entityManager.setFlushMode(FlushModeType.AUTO);
// COMMIT — flush тільки при commit
entityManager.setFlushMode(FlushModeType.COMMIT);
// ALWAYS — перед кожним запитом (рідко використовується)
// (Примітка: FlushModeType.ALWAYS застарів в Hibernate 5 і видалений в Hibernate 6)
Ручний flush для batch-операцій
@Transactional
public void batchUpdate(List<User> users) {
for (int i = 0; i < users.size(); i++) {
entityManager.merge(users.get(i));
if (i % 50 == 0) {
entityManager.flush(); // скинути 50 UPDATE в БД
entityManager.clear(); // очистити persistence context
}
}
// Фінальний flush для решти
entityManager.flush();
entityManager.clear();
}
🔴 Senior Level
Внутрішня реалізація
Процес flush:
1. Dirty checking
- Обхід всіх entities в persistence context
- Порівняння snapshot з поточним станом
- Для змінених — schedule UPDATE
2. Generation order
- INSERT спочатку (щоб отримати ID)
- UPDATE потім
- DELETE в кінці (щоб уникнути FK violations)
3. SQL generation та Execution
Порядок операцій
При flush Hibernate дотримується порядку:
1. Всі entity INSERT (в порядку persist())
2. Всі entity UPDATE (в порядку dirty detection)
3. Всі collection UPDATE
4. Всі collection DELETE
5. Всі entity DELETE (в порядку remove())
Це важливо для:
- Foreign key constraints
- Referential integrity
- Identity generation
Просунуті налаштування
spring:
jpa:
properties:
hibernate:
order_inserts: true # групування INSERT
order_updates: true # групування UPDATE
jdbc.batch_size: 50
Best Practices
✅ AUTO flush mode за замовчуванням
✅ Ручний flush для batch-операцій
✅ flush + clear кожні 50-100 entities
✅ COMMIT mode коли не потрібні актуальні дані
✅ order_inserts/order_updates для оптимізації
❌ ALWAYS mode (уникайте)
❌ Flush без причини
❌ Без clear після flush в батчах
🎯 Шпаргалка для співбесіди
Обов’язково знати:
- Flush — синхронізація даних з persistence context в БД
- Відбувається при: commit, entityManager.flush(), перед запитом (AUTO mode)
- FlushMode: AUTO (за замовчуванням), COMMIT (тільки при commit)
- Порядок операцій: INSERT → UPDATE → DELETE (для FK constraints)
- Для batch: flush + clear кожні 50-100 entities
Пов’язані теми:
- [[12. Що таке dirty checking в Hibernate]]
- [[7. Опишіть життєвий цикл Entity в Hibernate]]
- [[14. У чому різниця між persist() і merge()]]
- [[17. Як реалізувати оптимістичне блокування в JPA]]