데이터베이스의 상태를 변화시키기 위해 수행하는 작업 단위
를 말한다.
여기서 말하는 작업 단위는 프로젝트 별, 상황 별로 정의하기 나름이다.
예를 들어, 트랜잭션: 오늘 일기 작성하기...
(1)오늘 날씨 데이터를 가져와서, (2)일기를 DB에 저장하기
(1)과 (2)를 모두 수행해야 데이터베이스의 상태가 변화하므로, (1) + (2)를 하나의 트랜잭션이라고 본다.
트랜잭션A가 데이터를 1에서 2로 수정하고 커밋을 하기 전에 트랜잭션B가 데이터를 조회하면, 트랜잭션B는 데이터를 2로 인식하게 될 것이다.
하지만, 트랜잭션A가 그 상태에서 커밋되지 않고 롤백되었다면 데이터는 다시 1이 될 것이다.
이런 경우 트랜잭션B는 잘못된 데이터를 읽어가게 된다.
트랜잭션A가 데이터를 조회하고 다시 한번 조회하기 전에(두번의 조회 사이에) 트랜잭션B가 들어와 데이터를 수정후 커밋을 해버리게 되면 트랜잭션A가 두번째로 데이터를 조회했을 때 첫번째와 데이터 값이 달라지게 된다.
이렇게 되면 트랜잭션의 일관성을 만족시키지 못하게 된다.
Non-Repeatable Read
와 유사하게 트랜잭션A가 작업을 완료하기 전 트랜잭션B가 데이터를 수정, 커밋하여 일관성이 깨지게 된다.
💡Non-Repeatable Read :
특정 값
을 두고 트랜잭션끼리 경쟁했을 때 발생하는 문제
Phantom Read :특정 범위 내의 값
을 두고 트랜잭션끼리 경쟁했을 때 발생하는 문제
가장 일반적으로 사용하는 방법으로, 클래스
나 메서드
위에 어노테이션을 추가할 수 있다.
트랜잭션 기능이 적용된 프록시 객체 생성이 가능하다.
Rollback
또는 Commit
작업을 해준다.트랜잭션을 철저하게 강제할 것인지 혹은 어떠한 제약조건을 줄 것인지 설정할 수 있다.
트랜잭션에서 일관성이 없는 데이터를 허용하는 수준
해당 데이터
에 락이 걸려 조회할 수 없다. (Non-Repeatable Read 방지)모든 데이터
에 락이 걸린다. (Phantom Read 방지)@Transactional(isolation=Isolation.DEFAULT)
트랜잭션 동작 도중 다른 트랜잭션을 호출하는 상황에서 트랜잭션을 시작하거나 기존 트랜잭션에 참여하는 방법에 대해 결정하는 속성값. (함수A에서 함수B를 호출하는 경우)
💡NESTED 사용 예시
ex) 일기 작성 관련해서 로그를 DB에 저장하는 상황1. 로그 저장이 실패한다고 해서 -> 일기 작성까지 롤백되면 안됨
2. 일기 작성이 실패한다면 -> 로그 작성까지 롤백 되어야 함
트랜잭션을 읽기 전용 속성으로 지정할 수 있는 속성.
성능을 최적화 하기 위해서도 사용되지만, 어떤 트랜잭션에서 읽기 외에 쓰기,삭제,수정을 의도적으로 방지하기 위해서도 사용된다.
ReadOnly 속성을 설정한 경우 읽기 외의 쿼리가 실행되면 예외가 발생한다.
기본 옶션은 false
이므로 조회만 하는 로직의 경우 true
로 설정하여 실수를 잡아줄 수도 있다.
또한, true
의 경우 트랜잭션의 동작이 빨라진다.
@Transactional(readOnly=true)
예외가 발생했을 때 트랜잭션을 롤백 시킬 경우를 설정하는 옵션.
특정 Exception에 대해서는 롤백하지 않고 진행하고자 하는 경우 사용할 수 있다.
@Transactional(rollbackFor=Exception.class) -> 어떤 Exception이 발생하면 롤백한다.
@Transactional(noRollbackFor=Exception.class) -> 어떤 Exception이 발생해도 커밋한다.
Default: RuntimeException, Error
일정 시간 내에 트랜잭션을 끝내지 못하면 롤백하는 속성.
격리수준을 높여서 설정한 경우 timeout을 같이 설정하는 것이 좋다.
@Transactional(timeout=10) -> 10초 안에 완료되지 않으면 롤백한다.