Hai chiến lược xử lý xung đột khi nhiều transaction cùng sửa 1 row.
| Pessimistic | Optimistic | |
|---|---|---|
| Khóa DB | ✅ Khóa ngay khi đọc | ❌ Không khóa |
| Xung đột | Ngăn trước (tx khác chờ) | Phát hiện lúc commit |
| Hiệu năng | Thấp (chờ khóa, có thể deadlock) | Cao (không block) |
| Dùng khi | Xung đột thường xuyên, financial | Xung đột hiếm, CRUD thường |
Pessimistic — "chắc chắn có xung đột, khóa ngay khi đọc": dùng LockModeType.PESSIMISTIC_WRITE (tương đương SELECT ... FOR UPDATE) — giữ khóa row đến khi commit, transaction khác phải chờ.
Optimistic — "xung đột hiếm, kiểm tra lúc commit": thêm field @Version private Long version vào entity — mỗi UPDATE Spring tự thêm WHERE id = ? AND version = ?; nếu version đã bị transaction khác đổi → 0 row affected → OptimisticLockException → bắt để retry hoặc báo user "dữ liệu đã thay đổi, thử lại".
Best practice: Optimistic cho hầu hết CRUD; Pessimistic cho critical section (trừ số dư tài khoản, trừ kho số lượng ít).