동시성 문제, 격리

동시성 문제

같은 데이터에 동시 접근

웹처럼, 특정 값이 2가 있을 때 1로 바꾸기 위해 -1 했는데 2명이 동시에 하여, 0이 되버리는 상황

경쟁 상태 (Race Condition)

여러 클라이언트가 같은 데이터에 접근할 때 문제 발생

해결 방법

transaction isolation (격리)

서로 격리해서 다른 트랜잭션이 영향을 주지 못하게 함

쉬운방법
순서대로 실행하여 동시 접근 문제 자체가 없음. 하지만 너무 느림

다양한 격리 수준 지원

  • Read Uncommitted (거의 사용 안함)
  • Read Committed
  • Repeatable Read
  • Serializable

Read Committed

  • dirty read, dirty write를 해결
  • 커밋된 데이터만 읽기 -> 커밋된 값과 트랜잭션 진행 중인 값을 따로 보관
  • 커밋된 데이터만 덮어쓰기 -> 행 단위 잠금 사용 -> 같은 데이터를 수정한 트랜잭션이 끝날 때까지 대기

Repeatable Read

  • read skew 해결
  • Transaction 동안 같은 데이터를 읽게 함
  • 구현 예: MVCC(Multi-version Concurrency Control)
  • 읽는 시점에 특정 버전에 해당하는 데이터만 읽음

image

Serializable

  • 인덱스 잠금이나 조건 기반 잠금 등 사용
  • 읽는 동안 데이터 변경 2 해결

image

동시성 관련 다양한 문제들

  • 커밋되지 않은 데이터 읽기
  • 커밋되지 않은 데이터 덮어쓰기
  • 읽는 동안 데이터 변경 1st
  • 변경 유실
  • 읽는 동안 데이터 변경 2nd

커밋되지 않은 데이터 읽기 (dirty read)

image

커밋되지 않은 데이터 덮어쓰기 (dirty write)

image

읽는 동안 데이터 변경 (read skew)

  • 읽는 시점에 따라 데이터가 바뀜
  • 윗 사람 입장에서는 A의 값이 이상해짐

읽는 동안 데이터 변경 2 (read skew)

  • 한 트랜잭션의 결과가 다른 트랜잭션의 쿼리 결과에 영향
  • 같은 데이터를 쓰지 않지만 실제로는 경쟁 상태

변경 유실 (Lost Update)

  • 같은 데이터를 쓸 때 발생
  • 예) count 증가, 위키 페이지 수정
  • 기대하는건 readcnt 가 3이여야 하는데 2로 변경됨

image

변경 유실에 대한 처리 방법

원자적 연산

  • DB가 지원하는 원자적 연산 사용 > 동시 수정 요청에 대해 DB가 순차 처리
  • DB 지원 여부 확인

명시적 잠금

  • 조회 할 때 수정할 행을 미리 잠금
  • 예) select .. for update

image

CAS (Compare And png)

  • 수정할 때 값이 같은지 비교

image

Reference

아래의 URL를 정리한 글입니다.
https://www.youtube.com/watch?v=JJJ4LReZ5q4