비관적 락 (Pessimistic Lock)
비관적 락 (Pessimistic Lock) 이란?
- DB에서 제공하는 Lock 기능을 사용
- 엔티티가 아닌 스칼라 타입을 조회할 때도 사용가능
- Lock을 획득할 때까지 트랜잭션은 대기 - Lock Timeout 설정가능
JPA가 제공하는 비관적 락 옵션(LockModeType)
- PESSIMISTIC_WRITE : 베타락, 쓰기/읽기 Lock (Non-Repeatable Read를 방지)
- PESSIMISTIC_READ : 공유락, 읽기 Lock
- PESSIMISTIC_FORCE_INCREMENT : 베타락, 쓰기/읽기 Lock, 낙관적락처럼 버저닝따라서 버전에 대한 컬럼이 필요
(하이버네이트의 경우 nowait 를 지원하는 데이터베이스에 대해서 FOR UPDATE NOWAIT 옵션을 적용하고, 그렇지 않다면 FOR UPDATE 를 적용한다)
비관적 락 옵션(LockModeType) 적용 예제
@Repository
public interface UserMasterJpa extends JpaRepository<UserMasterEntity, String> {
/**
* JPA가 제공하는 비관적 락 옵션(LockModeType)
* LockModeType.PESSIMISTIC_READ
* LockModeType.PESSIMISTIC_WRITE
* LockModeType.PESSIMISTIC_FORCE_INCREMENT
*/
@Lock(LockModeType.PESSIMISTIC_READ)
Optional<UserMasterEntity> findByUserId(Long id);
}
Lock Timeout 적용 예제 - DBMS에서 제공안할 수 도 있음
@Repository
public interface UserMasterJpa extends JpaRepository<UserMasterEntity, String> {
/**
* Lock Timeout은 락을 잡고 있는 최대 시간을 설정
*/
@QueryHints({@QueryHint(name = "javax.persistence.lock.timeout", value ="10000")})
@Lock(LockModeType.PESSIMISTIC_READ)
Optional<UserMasterEntity> findByUserId(Long id);
}
Lock Scope 적용 예제 - DBMS에서 제공안할 수 도 있음
@Repository
public interface UserMasterJpa extends JpaRepository<UserMasterEntity, String> {
/**
* 락 범위(Lock Scope)를 지정
* NORMAL : 엔터티 자체를 잠급니다. 결합된 상속과 함께 사용하면 조상도 잠김
* EXTENDED : NORMAL 과 동일한 기능을 포함하며 조인 테이블에서 관련 엔터티를 차단할 수 있습니다.
*/
@QueryHints({@QueryHint(name = "javax.persistence.lock.scope", value = "EXTENDED")})
@Lock(LockModeType.PESSIMISTIC_READ)
Optional<UserMasterEntity> findByUserId(Long id);
}
Lock 을 사용함에 따라 발생할 수 있는 예외
- PessimisticLockException
(한 번에 하나의 Lock만 얻을 수 있으며, Lock을 가져오는데 실패하면 발생하는 예외) - LockTimeoutException
(락을 기다리다가 설정해놓은 wait time을 지났을 경우 발생하는 예외) - PersistanceException
(영속성 문제가 발생했을 때 발생하는 예외)
사용시 주의사항
- @Lock 어노테이션이 붙은 메서드 호출은 @Transaction 내부에서 동작함
- 만약 @Transaction 어노테이션의 영역(Scope) 밖에서 @Lock 어노테이션이 붙은 메서드를 호출한다면 아래와 같은 에러발생
(javax.persistence.TransactionRequiredException: no transaction is in progress)
'Java > JPA' 카테고리의 다른 글
JPA의 낙관적 락을 통해 엔티티에 대한 동시성 문제해결 (0) | 2023.09.02 |
---|