Spring

[Spring] 트랜잭션 전파

개바리여리 2025. 6. 29. 23:51

하나의 트랜잭션 안에서 또 다른 트랜잭션을 호출할 시,

기존 트랜잭션에 병합할지 하이면 새로운 트랜잭션으로 분류하여 독립적으로 실행할지

결정하는 정책이다.

 

전파에 대한 옵션 (Propagation)

REQUIRED (기본값) 기존 트랜잭션 있으면 참여, 없으면 새로 생성
REQUIRES_NEW 무조건 새 트랜잭션 생성, 기존 트랜잭션은 잠시 중단
NESTED 기존 트랜잭션 내에 논리적 중첩 트랜잭션 생성 (savepoint 사용)
SUPPORTS 트랜잭션이 있으면 참여, 없으면 그냥 실행 (비트랜잭션 가능)
NOT_SUPPORTED 트랜잭션을 무시하고 비트랜잭션으로 실행 (읽기 전용에서 주로 사용)
MANDATORY 반드시 트랜잭션 있어야 함, 없으면 예외 발생
NEVER 트랜잭션 있으면 예외 발생

 

 

timeout

트랜잭션 수행시간에 대한 타임아웃을 설정한다.

지정한 시간내에 완료되지 않으면 롤백을 수행한다.

기본값은 -1 (타임아웃 없음)이다.

@Transaction(timeout = 10)

 

rollbackFor
예외 발생시 체크예외도 옵션을 주어서 롤백을 해줄수 있다.

@Transactional(rollbackFor = Exception.class)

 

반대로 예외가 발생해도 롤백을 안하고 싶을땐

@Transactional(noRollbackFor=RuntimeException.class)

 

참고할 만한 블로그글 : 

https://hstory0208.tistory.com/entry/Spring-Transactional-%EC%98%B5%EC%85%98-%EC%95%8C%EC%95%84%EB%B3%B4%EA%B8%B0-%ED%8A%B8%EB%9E%9C%EC%9E%AD%EC%85%98-%EC%A0%84%ED%8C%8C

 

[Spring] @Transactional 옵션 알아보기 + 트랜잭션 전파

@Transactional에 대해 궁금하다면 아래 포스팅을 읽어보는 것을 추천드립니다. 트랜잭션이란? 특징과 사용법에 대해 쉽게 알아보자트랜잭션(Transaction) 트랜잭션은 DB의 상태를 변경시키기 위해 수

hstory0208.tistory.com

 

 

트랜잭션 격리 수준 

여러 트랜잭션이 동시에 데이터에 접근할 때 데이터의 정합성과 일관성을 어떻게 보장할 것인지를 정의하는 동시성 제어 정책

“다른 트랜잭션이 내 데이터 읽거나 수정하는 걸 어디까지 허용할까?” 에 대한 설정

 

동시에 여러 트랜잭션이 실행될 때 다음과 같은 문제가 생길 수 있습니다:


문제 설명
Dirty Read 아직 커밋되지 않은 다른 트랜잭션의 데이터를 읽음
Non-repeatable Read 같은 쿼리를 두 번 실행했을 때 결과가 다름
Phantom Read 조건에 맞는 행이 트랜잭션 중간에 추가/삭제되어 결과가 바뀜

 

격리 수준 4단계

 

격리수준 Dirty Read Non-repeatable Read Phantom Read
READ UNCOMMITTED O O O
READ COMMITTED (기본: Oracle) ❌ O O
REPEATABLE READ (기본: MySQL InnoDB) ❌ ❌ O
SERIALIZABLE ❌ ❌ ❌

 

 

1. READ_UNCOMMITTED

가장 낮은 격리수준으로 하나의 트랜잭션이 커밋되거 전에 그 변화가 다른 트랜잭션에 영향을 줄 수 있다,.

성능은 빠름, 하지만 Dirty Read 발생 가능 (매우 위험)

 

2. READ_COMMITED

다른 트랜잭션이 커밋하지 않은 정보를 읽을 수 없다.

대신 다른 트랜잭션이 읽은 로우를 또 다른 트랜잭션이 수정할 수 있어서 

같은 쿼리를 두 번 해도 결과가 바뀔 수 있음 (Non-repeatable Read)

 

3. REPEATABLE_READ

트랜잭션 동안 같은 쿼리 결과는 동일함

한 트랜잭션이 읽는 튜플을 다른 트랜잭션이 수정할 수 없지만 새로운 튜플(행)에 대한 추가는 막을 수 없다.

 

4. SERIALIZABLE

트랜잭션을 순차적으로 실행하게 된다.

모든 읽기/쓰기/삽입을 차단하여 가장 강력한 정합성 보장 , 성능은 가장 느리다.

 

 

이러한 옵션은 아래와 같이 설정할 수있다.

@Transactional(isolation = Isolation.READ_COMMITTED)
public void someMethod(){
	//작업 수행
}