[Spring] 트랜잭션 관리와 @Transactional 활용법(수정 예정)

눈치없어·2024년 8월 28일

Transaction: 데이터베이스의 상태를 변화시키기 위해 수행하는 작업 단위


트랜잭션의 ACID 특성

  • 원자성 (Atomicity)
    - 트랜잭션의 모든 연산이 성공적으로 완료되거나 전혀 수행되지 않아야 함을 보장함.
  • 일관성 (Consistency)
    - 트랜잭션이 실행된 후에도 데이터베이스의 일관된 상태가 유지되어야 함.
  • 고립성 (Isolation)
    - 트랜잭션이 실행되는 동안 다른 트랜잭션이 동시에 수행되더라도 서로의 영향을 받지 않아야 함.
  • 지속성 (Durability)
    - 트랜잭션이 성공적으로 완료된 후, 그 결과는 시스템이 실패하더라도 영구적으로 반영되어야 함

트랜잭션 사용 목적

  • 주로 DB에 문제가 생겼을 때 롤백(rollback)시키기 위해 사용.
  • commit: 트랜잭션의 모든 작업을 성공적으로 수행했음을 데이터베이스에 알리고 변경 사항을 영구적으로 반영
  • rollback: 트랜잭션의 수행 중 문제가 발생했을 때, 이전의 상태로 되돌려 모든 변경 사항을 취소.

여러 트랜잭션이 경쟁할 때 발생하는 문제

Dirty Read
한 트랜잭션이 아직 커밋되지 않은 데이터를 다른 트랜잭션에서 읽을 수 있음.
Non-Repeatable Read
같은 트랜잭션에서 동일한 데이터를 여러 번 읽을 때, 그 사이에 다른 트랜잭션이 데이터를 변경하여 서로 다른 결과가 나타남.
Phantom Read
한 트랜잭션에서 같은 조건으로 두 번 쿼리할 때, 사이에 다른 트랜잭션이 데이터를 추가하거나 삭제하여 결과 집합이 달라짐.


@Transactional 어노테이션

  • 클래스 또는 메서드 위에 붙여 트랜잭션 기능을 적용할 수 있음.
  • 트랜잭션이 적용된 프록시 객체를 생성.
  • 트랜잭션 관리자는 PlatformTransactionManager를 사용.

Spring 트랜잭션의 세부 설정들

  • Isolation (격리 수준):
    • 트랜잭션에서 일관성이 없는 데이터를 허용하는 정도를 설정.
    • 예시: @Transactional(isolation = Isolation.DEFAULT)
      • DEFAULT: 기본 설정값 (데이터베이스 설정을 따름)
      • READ_UNCOMMITTED: Dirty Read 발생 가능
      • READ_COMMITTED: Dirty Read 방지
      • REPEATABLE_READ: Non-Repeatable Read 방지
      • SERIALIZABLE: Phantom Read 방지
  • Propagation (전파 수준):
    • 트랜잭션 내에서 다른 트랜잭션을 호출할 때 기존 트랜잭션을 어떻게 처리할지를 설정.
    • 예시: @Transactional(propagation = Propagation.REQUIRED)
      • REQUIRED: 이미 시작된 트랜잭션이 있으면 참여하고, 없으면 새로 시작 (기본값)
      • SUPPORTS: 트랜잭션이 있으면 참여하고, 없으면 트랜잭션 없이 진행
      • REQUIRES_NEW: 항상 새 트랜잭션을 시작, 기존 트랜잭션 일시 정지
      • NESTED: 중첩 트랜잭션을 시작, 부모 트랜잭션과 독립적인 커밋과 롤백 가능
  • ReadOnly 속성:
    • 트랜잭션을 읽기 전용으로 지정하여 성능 최적화
    • 예시: @Transactional(readOnly = true)
  • 트랜잭션 롤백 예외 설정:
    • 특정 예외가 발생했을 때 트랜잭션을 롤백할지 여부를 설정
    • 예시:
      • @Transactional(rollbackFor = Exception.class): Exception 발생 시 롤백
      • @Transactional(noRollbackFor = Exception.class): Exception 발생 시 롤백하지 않음
    • 디폴트: RuntimeException, Error 발생 시 롤백
  • timeout 속성:
    • 지정된 시간 내에 트랜잭션이 완료되지 않으면 롤백
    • 예시: @Transactional(timeout = 10)
profile
dock 사이즈 다르잖아

0개의 댓글