대용량 처리 이해/Mysql

트랜잭션

훈지런 2022. 12. 27. 18:00

ACID


  • Atomicity
    • 원자적 연산을 보장해야 한다.
      • MVCC를 통해서
  • Consistency
    • 트랜잭션이 종료되었을 때 데이터 무결성이 보장된다.
      • 제약조건을 통해
  • Isolation
    • 트랜잭션은 서로 간섭하지 않고 독립적으로 동작한다.
      • 많은 성능을 포기해야하므로 개발자가 제어가능
      • 트랜잭션 격리레벨을 통해
  • Durability
    • 완료된 트랜잭션은 유실되지 않는다.
      • WAL을 통해

MVCC (Multi Version Concurrency Control)


Lock걸지 않고 데이터의 읽기 일관성을 보장해주는 내부 기법.
Lock : 한 트랜잭션이 Lock을 걸면 Lock가 풀리기 전까지 다른 트랜잭션에서 write를 못하거나 read, write 둘다 못한다.

MVCC는 이런 제약의 단점을 보완하기 위해 잠금을 사용하지않고 일관된 read를 보장

Mysql의 경우

MVCC 데이터베이스가 데이터의 업데이트가 필요할 때, 기존 데이터 항목을 새로운 데이터가 덮어쓰는 대신 데이터 항목의 새로운 버전을 만든다.
변경사항을 Undo Log 영역에 보관하고있다가 커밋이나 롤백하지않은 상태에서 조회하면 격리 수준에 따라서 데이터를 반환한다.

격리수준이 READ_UNCOMMITTED 인 경우에는 InnoDB 버퍼풀이나 베이터 파일에서 데이터를 반환한다.
그 이상의 격리수준인 경우엔 Undo Log 영역의 이전 내용의 데이터를 반환한다.

Undo Log


실행 취소 로그 레코드의 집합으로 트랜잭션 실행후 롤백 시 Undo Log 를 참조해 이전 데이터로 복구할수 있도록 로깅 해놓은 영역이다.

@Transactional 사용시 주의사항


동작방식이 프록시 방식임.
스프링이 뜰때 서비스를 상속받는 특정 객체를 만든다.
그래서 이너함수를 호출할때 트랜잭션이 제대로 먹지 않는다.

@Service
@Requiredargsconstructor
public class UserService{

    final private UserRepository UserRepository;

    public User create(long idx){
        return createUser(idx);
    }

        @Transactional   // 트랜잭션 동작하지 않음
    private createUser(long idx){
        // User 생성 조회 업데이트 등등...
    }
}
  • 트랜잭션 범위는 최대한 짧게 걸어주자!

트랜잭션 격리레벨


MySQL 격리레벨

  • Read Uncommitted
  • Read Committed
  • Repeatable Read
  • Serializable Read

이상현상

  • Dirty Read
    • 커밋되지 않은 데이터를 읽음
  • Non Repeatable Read
    • 같은 데이터를 읽었는데 결과가 달라짐
  • Phantom Read
    • 같은 데이터를 읽었는데 없던 결과가 생김
Dirty Read Non Repeatable Read Phantom Read
Read Uncommitted O O O
Read Committed O O
Repeatable Read O
Serializable Read

Read Uncommitted
Read Committed
Repeatable Read
Serializable Read
점점 동시 처리량이 낮아진다.

'대용량 처리 이해 > Mysql' 카테고리의 다른 글

동시성 제어  (0) 2022.12.28
CAP이론  (0) 2022.12.26
페이지네이션 최적화  (1) 2022.12.25
정규화  (0) 2022.12.24
인덱스  (3) 2022.12.23