6장은 기본 SQL문법을 다루는데 굳이 정리할 필요를 느끼지 않아서 작성하지 않았다.
데이터베이스의 상태를 변화시키기 해서 수행하는 작업의 단위를 뜻한다.
하나 이상의 쿼리가 트랜잭션의 단위가 된다.
예를 들면,
A가 B에게 송금 할 때
위 두가지 처리가 하나의 트랜잭션이 된다.
트랜잭션의 결과는 전부 성공하거나 전부 실패해야한다.
트랜잭션 진행 중 실패가 일어난다면 ROLLBACK을 실행해 트랜잭션 실행 이전으로 돌아간다.
"트랜잭션이란?"에서 설명한 예시에서 1번이 완료된 이후 2번에서 실패가 일어났지만 1번이 그대로라면 A는 돈을 잃고, B는 돈을 받지 못하는 문제가 발생한다.
일련의 데이터 조작 전후에 그 상태를 유지해야한다.
데이터베이스 오브젝트에 정합성 제약을 추가하여 유지한다.
각각의 유저가 고유한 ID를 가져야 한다면 ID 컬럼에 UNIQUE 조건을 추가하여 ID 컬럼의 값이 중복되지 않도록 할 수 있다.
일련의 데이터 조작을 여러 사용자가 동시에 실행되도 각각의 처리가 모순 없이 실행되는 것을 보장한다.
여기에서 설명한 '모순 없다'는 것은 무슨 뜻일까?
복수의 트랜잭션이 순서대로 실행되는 경우와 같은 결과를 얻을 수 있는 상태를 말한다.
이것을 트랜잭션 격리 수준(Transaction Isolation Level)이라고 하는데, 자세한 내용은 다른 글을 참고하길 바란다.
A와 B, 두 사용자가 있다. 하나의 컬럼의 값을 변경하려고 한다.
1이 진행되는 중에 두 사용자가 같은 계좌을 조회한다면 같은 값을 조회하게 된다.
이를 10이라고 가정했을 때, 2를 진행하게 되면 A는 10 - 1인 9로 값을 변경한다.
마찬가지로, B 역시 9로 값을 변경한다.
두 사용자 모두 같은 계좌에서 1 씩 감소시켰고, 결과는 8 이 되야하지만 9이다.
이러한 일을 막기 위해서 테이블이 수정 될 때 다른 사용자가 접근하지 못하도록 LOCK을 걸어서 후속 처리를 BLOCK한다.
일련의 데이터 조작을 완료하고 완료 통지를 받는 시점에 그 조작은 영구적으로 되어 그 결과를 잃지 않는 것을 말한다.
이는 시스템이 정상일때 뿐만 아니라 데이터베이스나 OS의 이상 종료, 즉 시스템 장애도 견딜 수 있다는 뜻이다.
지속성을 보장하기 위해 많은 DBMS에서는 트랙잭션 조작을 하드디스크에 로그 라는 형태로 기록하고 있다.
시스템에 이상이 발생하면 로그를 이용해 이상 발생 전의 상태까지 복원한다.
기본적으로 DDL 이나 DML에 의한 데이터 저장은 트랜잭션이 커밋되기 전까지는 다른 커낵션에서 보이지 않는다.
하지만 이에 상관없이 다른 커녁션에서 보이는 경우가 있다.
트랜잭션의 개시가 명시적으로 지정되지 않았을 때 구별하는 방법으로 2가지 모드가 있다.
여기서 1 번 (오토커밋)인 경우 자신이 COMMIT을 명시하지 않아도 자동적으로 COMMIT이 되기 때문에 다른 커넥션에서 보이게 된다.
DBMS 마다 차이가 있지만 Oracle이나 MySQL에서는 DDL 문 실행시 암묵적인 커밋이 발생한다.
'갱신'과 '참조'는 서로를 블록하지 않지만, '갱신'과 '갱신'이 부딪치는 경우 늦게 온 갱신이 대기 상태가 된다.
이 때 잠금을 건 쪽이 언제 잠금을 풀지 알 수 없으니 기다리지 않거나, 기다린다면 얼마나 기다릴지 설정할 수 있다.
기다리는 시간이 설정했던 시간보다 길어진다면 잠금 타임아웃이 발생하는 것이다.
트랜잭션 A와 B 가 있고, 테이블 a, b가 있다.
트랜잭션 A는 테이블 a의 잠금을 얻고 b를 갱신하고자 한다.
트랜잭션 B는 테이블 b의 잠금을 얻고 a를 갱신하고자 한다.
이 경우 아무리 기다려도 상황이 바뀌지 않는 상태가 되는데 이를 교착 상태라고 한다.
별 이유가 없다면 아래 방식의 트랜잭션은 사용하지 않는 것이 좋다.
여러 DBMS에서 기본적으로 오토커밋을 사용하는데 간단한 쿼리의 실행과 테스트를 하는 경우에는 편리하지만 그 이외의 경우에는 부하가 커 추천하지 않는다.