이전 글 [ https://techforme.tistory.com/59 ]
이전 글에서 동시성 제어를 위한 기술인 'Lock' 에 대해서 알아보았다. Lock 이 어떤식으로 Transaction 의 Schedule 을 컨트롤 하는지, 그리고 Lock 획득하고 반환하는 절차에 따라 어떤 영향(Deadlock 발생, Recoverability 보장)이 나타나는지에 대해서도 알아보았다.
Lock 의 경우 Read 와 Write 가 상호 배타적으로 작업을 수행하게 되는데 (Read Lock 이 걸린 자원에 대해서는 Write Lock 을 획득할 수 없거나 반대로 Write Lock 이 걸린 자원은 Read Lock 획득이 불가능함) 이런 경우 Concurrency 가 상당히 떨어지기 때문에 성능면에서 아쉬울 수 밖에 없다. 때문에 Mysql 과 Postgresql 을 비롯한 많은 RDB 에서는 MVCC 라는 기술을 통해 이를 극복하여 Transaction Throughput 을 극대화 한다.
이번 글에서는 Read 와 Write 의 동시 접근을 허용하는 MVCC 기술에 대해서 알아본다.
1. MVCC(Multi Version Concurrency Control)
1) MVCC 란 ?
MVCC 는 전통적 동시성 제어 기술인 'Lock' 이 Read 와 Write 를 상호 배타적으로 수행하는데에 반해, Read 와 Write 가 서로를 block 하지 않고 동시에 접근하는 것을 허용함으로써 Concurrency 를 향상 시킬 수 있는 기술입니다. MVCC 는 Transaction 수행 시 접근하는 데이터의 Snapshot 을 생성하여 데이터의 Version 을 별도로 관리하며, 이를 통해 Transaction 의 일관성을 보장하여 줍니다. (Transaction 이 처리 중인 상황에서 다른 Transaction 이 해당 데이터의 값을 변경해도 이전 데이터의 값을 Snapshot 형태로 유지하고 있기 때문에 데이터의 일관성을 유지할 수 있습니다.) Multi-Version 이라는 말은 트랜잭션 마다 특정 데이터에 대해서 각각의 버전을 생성하기 때문에 붙여진 이름입니다.
2) MVCC 의 특성
동작 방식이 직관적인 Lock 과는 달리 MVCC 는 RDB 마다 조금씩 다르고 Isolation Level 에 따라서 MVCC 를 활용하는 방식도 다릅니다. 그러나 중요한 공통적 특성이 있습니다.
- MVCC 는 commit 된 데이터만을 읽습니다.
- 변화이력을 관리하기 때문에 특정 시점을 기준하여 데이터를 읽을 수 있습니다.
이러한 특성이 어떻게 활용 되는지는 아래 MVCC 를 이용한 동시성 제어 예시를 통해 더 알아보겠습니다.
2. MVCC 의 동시성 제어 방식
아래는 Non-Repeatable Read 문제를 발생할 수 있는 간단한 상황입니다.
초기 : X = 100
Tx 1 : X 값을 두번 Read
Tx 2 : X 값을 200 으로 Write
위 Transaction 이 동시에 요청해온 경우, 아래와 같은 시나리오를 떠올릴 수 있습니다.
Tx 1 : --> Read X = 100 ------------------------------> Read X = ? -----|
Tx 2 : -------------------> Write X = 200 --> Commit ------------------|
아마도 두번째 조회 쿼리가 발생 되기 이전에 Tx 2 에서 X = 200 이라는 값이 Commit 되었으므로 X = 200 이 조회될 것입니다. 이전에 X = 100 이 조회 이는 Isolation 을 위반하는 결과입니다.(Non-Repeatable Read) 이때 Repeatable Read 레벨의 Isolation 을 적용하게 되면 MVCC 기술을 이용하여 다음과 같이 이 문제를 해결 할 수 있습니다.
MVCC 기술은 Transaction 을 시작하는 시점에 접근 데이터에 대하여 Snapshot 을 저장해둡니다. 이를 통해 Transaction 이 진행되는 동안 다른 Transaction 의 commit 과 무관하게, 일관된 Read 결과를 보여줄 수 있습니다. (MySQL 에서는 이를 Consistent Read 라고 지칭합니다. PostgreSQL 에서도 동일한 매커니즘으로 동작 합니다.)
참고로 Lock 방식의 제어에서는 Read / Write를 상호 배제하므로 Tx 1 이 완전히 수행된 후, Tx 2 가 순차적으로 일어나게 됩니다. MVCC 는 이러한 점에 대해 Lock 방식보다 동시성이 뛰어나며 처리속도가 빠릅니다.
3. 결론
이번 글에서는 Transaction 처리를 위한 MVCC 기술에 대해서 아주 간단히 알아보았습니다. 사실 MVCC 는 위와 같은 상황 이외에도 여러 목적으로 활용됩니다. 그와 관련해서는 다른 글에서 더 알아보도록 하겠습니다.