프레임워크 & 라이브러리/JPA
[JPA] 낙관적 락 & 비관적 락
괴발맨
2023. 4. 9. 22:03
낙관적 락 & 비관적 락
낙관적 락
- JPA가 제공하는 버전 관리 기능 사용 (
@Version
) - 즉, 애플리케이션 단에서 구현된 락
- 엔티티의 버전과 DB의 버전이 다르면 예외 발생
비관적 락
- 데이터베이스가 제공하는 락 기능 사용
- 락 걸렸을때 타임아웃 설정 가능
- ex) select for update
용도 -> JPA는 DB 트랜잭션 격리수준을 READ COMMITED 정도로 가정하나, 더 높은 격리 수준이 필요할때 사용
JPA 락 옵션 (javax.persistance.LockModeType)
NONE
- 락 X
OPTIMISTIC
- 낙관적 락
OPTIMISTIC_FORCE_INCREMENT
- 낙관적 락 + 버전정보 강제 증가
PESSIMISTIC_READ
- 비관적 락, 읽기 락
PESSIMISTIC_WRITE
- 비관적 락, 쓰기 락
NONE
- @Version 필드 존재하면 낙관적 락 적용
- 엔티티 수정 시 버전 체크 & 증가. 버전 값이 현재 버전이 아니면 예외 발생
UPDATE my_table SET my_col = 'updated', version={현재 버전 + 1} where id = 1 and version = 현재 버전
-> 현재 버전에 해당하는 로우가 존재하지 않으면 예외
OPTIMISTIC
- 엔티티를 수정하지 않아도 버전 확인
- 즉, 조회만 해도 해당 트랜잭션 커밋 시점에 버전 체크.
- 조회 중 다른 트랜잭션이 같은 엔티티 수정 불가
OPTIMISTIC_FORCE_INCREMENT
- 엔티티를 수정하지 않아도 버전 강제로 증가.
- 엔티티 버전과 DB의 버전이 다르면 예외 발생
- 조회 & 수정 모두 하면 버전 + 2 증가
- 예시: 게시물 조회 -> 첨부파일 추가
- 이 경우 게시물 엔티티를 조회만 하기 때문에 버전 증가 필요
PESSIMISTIC_WRITE
- select for update 쿼리 사용
PESSIMISTIC_READ
- 데이터 반복 읽기만 하고 수정하지 않을때 사용
- 일반적으로 잘 사용되지 않음
PESSIMISTIC_FORCE_INCREMENT
- @Version 사용 -> 버전 강제 증가
- select for update nowait을 DB가 지원하면 사용