속성별 반응
핵심 차이는 부모 경계와의 관계
| 속성 | 부모가 있으면 | 없으면 |
|---|---|---|
| REQUIRED 기본 서비스 경계 | 그 경계에 참여해서 함께 커밋/롤백 | 새 트랜잭션 시작 |
| REQUIRES_NEW 독립 기록·알림 | 부모를 잠시 중단하고 별도 커밋 | 새 트랜잭션 시작 |
| NESTED 부분 실패 허용 | SAVEPOINT로 자식만 되돌릴 수 있음 | 새 경계처럼 시작 |
| SUPPORTS 있으면 같이 감 | 있으면 참여 | 트랜잭션 없이 실행 |
| NOT_SUPPORTED 트랜잭션 밖 작업 | 부모를 중단하고 밖에서 실행 | 트랜잭션 없이 실행 |
| MANDATORY 상위 경계 필수 | 반드시 참여 | 예외 발생 |
| NEVER 트랜잭션 금지 | 예외 발생 | 트랜잭션 없이 실행 |
주문 생성 예시
커밋 경계를 어떻게 분리하는가
부모 트랜잭션
@Transactional createOrder()
주문 저장과 재고 차감은 같은 결과로 묶고 싶으므로 기본은 REQUIRED입니다.
주문과 무관하게 남길 기록
auditService.log(order)
REQUIRES_NEW
부모가 롤백돼도 감사 로그는 별도 커밋으로 남습니다.
실패해도 주문은 살리고 싶은 부가 작업
pointService.addPoints(order)
NESTED
포인트 적립만 SAVEPOINT 기준으로 롤백하고, 주문 생성은 유지할 수 있습니다.
실무에서는 기본은 REQUIRED, 결과를 따로 남겨야 하면 REQUIRES_NEW,
부모는 유지한 채 일부만 취소하고 싶으면 NESTED를 먼저 검토합니다.