본문 바로가기
spring/스프링

트랜잭션

by ddanss 2023. 3. 20.
728x90

트랜잭션

- 하나의 거래를 안전하게 처리하도록 보장해주는 것

 

commit : 모든 작업이 성공해서 데이터베이스에 정상 반영하는 것

Rollback : 작업 중 하나라도 실패해서 거래 이전으로 되돌리는 것

 

트랜잭션 ACID

1. 원자성(Atomicity)

- 트랜잭션 내에서 실행한 작업들은 마치 하나의 작업인 것처럼 모두 성공하거나 모두 실패해야 한다

2. 일관성(Consistency)

- 모든 트랜잭션은 일관성 있는 데이터베이스를 유지해야한다. 데이터베이스에서 정한 무결성 제약 조건을 항상 만족해야함

3. 격리성(Isolation)

- 동시에 실행되는 트랜잭션들이 서로에게 영향을 미치지 않도록 격리. 동시에 데이터 수정 못하게. 동시성과 관련된 성능 이슈로 인해 트랜잭션 격리 수준(Isolation level)을 선택할 수 있음

4. 지속성(Durability)

- 트랜잭션을 성공적으로 끝내면 그 결과가 항상 기록되어야함. 중간에 시스템에 문제가 발생하더라도 데이터베이스 로그 등을 사용해서 성공한 트랜잭션 내용을 복구해야함

 

트랜잭션 격리수준 - Isolation level

1. READ UNCOMMITED(커밋되지 않은 읽기)

2. READ COMMITTED(커밋된 읽기)

3. REPEATABLE READ(반복 가능한 읽기)

4. SERIALIZABLE(직렬화 기능)

 

자동 commit

- 각각의 쿼리 실행 직후에 자동으로 commit을 호출

set autocommit true; //자동 커밋 모드 설정
insert into member(member_id, money) values ('data1',10000); //자동 커밋

수동 commit

set autocommit false; //수동 커밋 모드 설정
insert into member(member_id, money) values ('data1',10000);
commit; //수동 커밋

***** 수동 커밋 모드나 자동 커밋 모드는 한번 설정하면 해당 세션에서는 계속 유지된다. 중간에 변경하는 것은 가능

 

DB락

1. 세션1이 트랜잭션 시작

2. 세션1이 변경시도, 세션1이 락 획득

3. 세션1은 락을 획득했으므로, 변경 sql을 수행

4. 세션2도 트랜잭션 시작

5. 변경시도하려했으나 락이 없으므로 락이 돌아올때까지 대기 (락 대기시간을 넘어가면 락 타임아웃 오류 발생)

6. 세션1 커밋 수행 -> 락 반납

7. 대기하던 세션2가 락 획득

8. 변경sql수행 

9. 세션2는 커밋 수행 후 트랜잭션이 종료되었으므로 락 반납

 

select for update : 데이터를 조회할때 락 획득

 

조회 시점에 락이 필요한 경우

- 트랜잭션 종료 시점까지 해당 데이터를 다른 곳에서 변경하지 못하도록 강제로 막아야 할  때

 

트랜잭션과 락은 데이터베이스마다 동작하는 방식이 조금씩 다르기 때문에, 해당 데이터베이스 매뉴얼을 확인해보고, 의도한대로 동작하는지 테스트한 이후에 사용

 

커넥션 유지

1. 커넥션 유지가 필요한 메서드는 파라미터로 넘어온 커넥션을 사용해야 한다. 따라서 con = getConnection()코드가 있으면 안된다

2. 커넥션 유지가 필요한 두 메서드는 리포지토리에서 커넥션을 닫으면 안됨. 커넥션을 전달받은 리포지토리뿐만 아니라 이후에도 커넥션을 계속 이어서 사용하기 때문. 이후 서비스 로직이 끝날때 트랜잭션을 종료하고 닫아야함

 

코드

Connection con = dataSource.getConnection();

con.setAutoCommit(false); //수동커밋, 트랜잭션 시작

con.commit(); //성공시 커밋

con.rollback(); // 실패시 롤백

con.close 이용해서 종료해줘야함

반응형

댓글