[Spring] @Transactional

Coastby·2022년 11월 6일
0

LIKELION Back-End School

목록 보기
55/61
post-custom-banner

1. 트랜잭션 (Transaction) 이란?

트랜잭션은 우리말로 '거래'라는 뜻을 갖고 있다.

실제 거래에서 네이버의 안전거래로 트랜잭션의 개념을 이해할 수 있다.

  • 구매자가 입금을 한다.
  • 판매자는 입금을 확인 후 상품을 보낸다
  • 구매자가 상품을 확인 후 구매완료를 누른다.
  • 판매자에게 입금이 되고, 거래가 종료된다.
    만약, 판매자에게 입금하는 작업이 성공했더라도 원하던 물건을 받지 못했다면 입금이 취소되었을 것이다.

모든 작업들이 성공적으로 완료되어야 작업 묶음의 결과를 적용하고, 어떤 작업에서 오류가 발생했을 때는 이전에 있던 모든 작업들이 성공적이었더라도 없었던 일처럼 완전히 되돌리는 것이 트랜잭션의 개념이다.

데이터베이스를 다룰 때 트랜잭션을 적용하면 데이터 추가, 갱신, 삭제 등으로 이루어진 작업을 처리하던 중 오류가 발생했을 때 모든 작업들을 원상태로 되돌릴 수 있다. 모든 작업들이 성공해야만 최종적으로 데이터베이스에 반영하도록 한다.

트랜잭션 구성은 @Configuration, XML 기반 설정 말고도 애노테이션 기반으로 설정할 수 있다.

애노테이션 방식은 선언적 트랜잭션이라고 불리고, 선언 시 트랜잭션 기능이 적용된 프록시 객체가 생성된다.
@Transactional으로 생성된 프록시 객체는 @Transactional이 적용된 메소드가 호출될 경우,
PlatformTransactionManager를 사용하여 트랜잭션을 시작하고, 정상 여부에 따라 Commit/Rollback 동작을 수행한다.
트랜잭션 처리를 JDK Dynamic Proxy 객체에게 대신 위임하여 AOP로 동작하게 된다.

○ Transaction ACID

  • 원자성(Atomicity)
    • 한 트랜잭션 내에서 실행한 작업들은 하나의 단위로 처리
    • 모두 성공하거나 모두 실패
  • 일관성(Consistency)
    • 트랜잭션은 일관성 있는 데이터베이스 상태를 유지
  • 격리성(Isolation)
    • 동시에 실행되는 트랜잭션들이 서로 영향을 미치지 않도록 격리
  • 영속성(Durability)
    • 트랜잭션을 성공적으로 마치면 결과가 항상 저장

2. 서비스환경에서의 @Transactional

DB와 관련된 트랜잭션이 필요한 서비스 클래스 혹은 메서드에 @Transational 어노테이션을 달아주면 트랜잭션 처리가 된다.

@Transational이 붙은 메서드는 메서드가 포함하고 있는 작업 중에 하나라도 실패할 경우 전체 작업을 취소한다.

3. 테스트환경에서의 @Transational

테스트 메서드에 @Transational을 사용하면 트랜잭션으로 감싸지며, 메서드가 종료될 때 자동을 롤백된다.

○ TestTransaction 클래스

org.springframework.test.context.transaction.TestTransaction
TestTransaction 클래스는 @Transactional이 적용된 테스트 메서드를 감싸고 있는 트랜잭션과 상호 작용할 수 있는 기능을 가진 유틸리티 클래스다.

○ 롤백되지 않는 경우

  • WebEnvironment의 RANDOM_PORT, DEFINED_PORT를 사용하면 실제 테스트 서버는 별도의 스레드에서 테스트를 수행하기 때문에 트랜잭션이 롤백되지 않는다.
  • Auto Increment가 적용된 id : 다시 감소하지 않는다.

4. 결론

프로덕션 환경과 테스트 환경 각각에서의 동작 방식이 다름을 유념하여 사용하자.

프로덕션 환경 : 일련의 작업들을 묶어서 하나의 단위로 처리하고 싶을 때
테스트 환경 : 테스트 메서드가 마친 후 데이터를 롤백하고 싶을 때

참고 : https://tecoble.techcourse.co.kr/post/2021-05-25-transactional/
https://data-make.tistory.com/738

profile
훈이야 화이팅
post-custom-banner

0개의 댓글