사실 Transaction 의 4대 속성
A : Atomicity (원자성) - 절대로 쪼개지면 안됨. 쪼개질 수 없다.
C : Consistency (일관성) - 실행을 완료하면 모든 데이터가 모두 기록되어야 함.
I : Isolation (격리성) - 트랜젝션 실행 중에는 다른 트랜젝션이 개입하지 못함.
D : Durability (지속성) - 트랜젝션에 성공했으면 영구적으로 dB 에 반영되어야 함.
동시에 두 개의 프로세스가 한 데이터에 접근하려고 하면 오류남. 그걸 해결하려면,
프로세스 : (Race condition) → (상호 배제) → (critical section) → (세마포어, 뮤텍스)
여러 개의 데이터에 관련이 되어있으면, 하나가 실패하면 모두다 실패한 것임.
하나라도 실패하면 roll back 해야 함.
잠금하고, 작업이 느려지면, 모든 시스템이 다 느려짐. 기다려야 하기 때문.
단순하게 읽기만 할건데, 잠겨있으면? 기다리다 죽음.
Exclusive Lock : 내가 쓰는 중에는 읽기, 쓰기, 수정 다 불가능
Shared Lock : 내가 쓰는 중에 읽기 가능
오라클이 트랜잭션 관리를 잘 함. 그래서 널리 쓰임
서로 다른 DB에서 모두 다 끝나면 끝난걸로 확인
IBM : CORBA, MS : COMT
메모리에서 잠근다!
메모리에는 페이지와 레코드가 있다
X Lock : 나만 보겠다. 아무도 읽지도 말고 쓰지도 마
S Lock : 나는 쓸 수 있는데 다른 사람은 읽기만 가능
R 레코드 잠금 : 하나의 투플을 잠그는 것
P 페이지 전체 잠금 :
I 인덱스 잠금
T 테이블 잠금
mysql 은 X,S,R,P,I 만 있음
자바에서는 모든 트랜잭션이 순서대로 실행된 결과를 보장하기 위해 메소드에 Syncronized 키워드를 붙임. 그래서 모든 트랜젝션이 나열(Serialize)이 되도록 동기화 함 → Thread safe 함. 병행성 제어면에서는 좋은데, 성능이 떨어짐.
Vector : 배열로 만들어진 List. (Array list 와 같음). thread safe 하게 만들어짐.
그런데, 너무 느려서 Syncronized 를 빼고 array list 로 바꿈.
가장 널리 사용되는 잠금 규약으로, 두 가지 규칙을 사용
DB 에서 Transaction 에 대한 잠금 규약
트랜잭션 T가 어떤 객체를 판독(수정)하려면, 그 객체에 대해 공유(배타적) 잠금을 요청
트랜잭션이 종료될 때 가지고 있던 모든 잠금을 풀어줌
잠금 규약은 안전한 인터리빙만을 어용함
두 트랜잭션이 동일한 객체에 접근하며, 한 트랜잭션이 객체를 수정하려 할 때, 단위 작업이 직렬 순서로 수행한 효과를 얻도록 함
T1이 A를 막고, T2가 B를 막았는데, T1이 B 를 접근하려고 하고, T2 를 A가 접근하려고 한다.
해결방법
트랜잭션마다 우선순위를 부여해주고 우선 순위가 낮은 트랜잭션은 우선순위가 높은 트랜잭션을 기다릴 수 없도록 하여 예방
Dirty Read : Record 잠금
Phantom Read : Index 잠금
Repeatable Read : Page 잠금