DB는 트랜잭션이라는 기능을 제공한다.
- INSERT나 UPDATE 명령으로 데이터를 추가, 갱신할 때도 트랜잭션 기능을 사용한다.
START TRANSACTION
COMMIT
ROLLBACK
- 지금까지 특별히 의식할 필요가 없던 이유는 자동 커밋이라 불리는 기능이 동작했기 때문이다.
트랜잭션
정규화에 의해 분할된 주문 테이블과 주문상품 테이블의 관계를 생각해보자
주문 테이블에 행이 존재한다면 주문상품 테이블에는 적어도 하나의 행이 존재해야 한다.
- 그렇지 않으면 주문한 상품이 없는데 주문이 된 상태가 된다.
- 테이블 사이에는 의존관계가가 존재한다.
발주처리
주문이 발생했을 때 생각해보자
- 발주처리에 관한 것으로 먼저 주문번호를 지정해야 한다.
- 기존 주문과 구분되는 주문번호를 발행하는 처리가 필요하다.
자동 증가를 사용하거나 ‘번호 중 가장 큰 값을 SELECT 명령으로 가져와 그 값에 +1을 더한다.’라는 처리가 필요하다.
- 최대값은 MAX()로 검색할 수 있으므로 ‘MAX + 1’ 이라 할수도 있다.
번호를 발행 받으면 해당 번호를 키로 삼아 INSERT가 이루어진다.
- 주문 테이블에는 INSERT 한번, 주문상품 테이블에는 주문된 상품 수 만큼 INSERT 명령이 실행된다.
- 복수의 테이블에 INSERT 되므로 실행되는 명령은 최소 두번이다. (중요)
#트랜잭션 없이 에러가 발생한 상황
INSERT INTO 주문 VALUES(4, '2023-02-23', 1);
INSERT INTO 주문상품 VALUES(4, '0003', 1);
INSERT INTO 주문상품 VALUES(4, '0004', 2);
INSERT 명령이 특정 원인으로 인해 에러가 발생한 경우를 가정해보자
- 트랜잭션 기능을 사용하지 않을 때는 문제없이 실행된 INSERT 명령을 실행 전으로 되돌릴 수 없으므로 따로 DELETE 명령을 실행해 지워야한다.
롤백과 커밋
몇 단계로 처리를 나누어 SQL 명령을 실행하는 경우에 트랜잭션을 자주 사용한다.
- 트랜잭션을 사용해서 데이터를 추가한다면 에러가 발생해도 트랜잭션을 롤백(rollback)해서 종료할 수 있다.
- 롤백하면 트랜잭션 내에서 행해진 모든 변경사항을 없었던 것으로로 할 수 있다.
- 에러가 발생하지 않으면 변경사항을 적용하고 트랜잭션을 종료하는데 이때 커밋(commit)을 사용한다.
트랜잭션을 롤백하면 변경한 내용이 적용되지 않기 때문에 DELETE 명령으로 삭제하는 처리가 필요하지 않는다.
자동커밋
트랜잭션을 사용해서 데이터를 추가할 때는 자동커밋을 꺼야 한다.
- MySQL 클라이언트에서 명령을 실행할 때는 자동커밋이 켜져 있는 상태이다.
- INSERT, UPDATE, DELETE가 처리될 때마다 트랜잭션은 암묵적으로 자동커밋 상태로 되어있다.
자동커밋을 끄기 위해서는 명시적으로로 트랜잭션의 시작을 선언할 필요가 있다.
- 트랜잭션을 시작할 때는 START TRANSACTION 명령을 사용한다.
#트랜잭션 시작
START TRANSACTION
- 트랜잭션을 종료하기 위해서는 변경된 내용을 적용한 후에 종료하는 ‘커밋’과 적용하지 않고 종료하는 ‘롤백’의 두가지 방식이 있다.
#트랜잭션 내에서 실행한 명령을 적용한 후 종료하기
COMMIT
#트랜잭션 내에서 실행한 명령을 파기한 후 종료하기
ROLLBACK
트랜잭션 내에서 실행된 SQL 명령은 임시 데이터 영역에서 수행된다.
- COMMIT 명령을 내리면 임시 데이터 영역에서 정식 데이터 영역으로 변경이 적용된다.
- ROLLBACK 명령을 내리면 임시 데이터 영역에서의 처리는 버려지게 된다.
#에러가 발생하지 않은 경우 트랜잭션은 COMMIT을 이용해 종료
START TRANSACTION;
INSERT INTO 주문 VALUES(4, '2023-02-23', 1);
INSERT INTO 주문상품 VALUES(4, '0003', 1);
INSERT INTO 주문상품 VALUES(4, '0004', 2);
COMMIT;
트랜잭션을 시작해서 SQL 명령을 실행하고 COMMIT 또는 ROLLBACK명령으로 트랜잭션을 종료하는 일련의 처리방법을 ‘트랜잭션을 걸어서 실행한다’ 또는 ‘트랜잭션 내에서 실행한다’라고 말한다.
- 트랜잭션을 사용해서 처리하는 것으로 간단히 데이터를 관리할 수 있다.
트랜잭션 사용법
발주처리와 같은 데이터 등록처리 과정에서는 대부분 트랜잭션 내에서 여러 개의 SQL 명령을 실행하게 된다.
- 하나의 명령에 트랜잭션을 걸어 실행하는 것은 별로 의미가 없다.
- 트랜잭션 내에서 실행하는 복수의 SQL 명령은 세트 단위로 유효/무효가 된다.
- 반드시 세트로로 실행하고 싶은 SQL 명령을 트랜잭션에서 하나로 묶어 실행한다는 뜻이다.
세트로 실행하고 싶은 SQL 명령은 트랜잭션 내에서 실행한다.
ROLLBACK은 에러가 발생한 경우 변경사항이 적용되지 않도록 하는 목적으로로 주로 사용한다.
- 에러가 발생하지 않아도 ROLLBACK을 하면 변경한 내용은 파기된다.
에러가 발생하더라도 COMMIT을 하면 문제없이 실행된 SQL 명령의 변경사항은 데이터베이스에 그대로 반영된다.
MySQL의 경우에만 트랜잭션을 시작할 때 ‘START TRANSACTION’명령을 사용한다.
- MySQL에서는 ‘START TRANSACTION’ 외에도 ‘BEGIN’을 사용할 수도 있다.
SQL SERVER나 PostgreSQL에서는 ‘BEGIN TRANSACTION’ 명령을 사용한다.
Oracle이나 DB2에서는 트랜잭션을 시작하는 명령은 따로 없다.
- 표준화가 진행되지 못한 부분이다.
자동커밋은 클라이언트 툴의 기능이다.
- 미들웨어도 데이터베이스 접속 시 대부분 자동커밋을 한다.
미들웨어는 서로 다른 애플리케이션이 서로 통신하는 데 사용되는 소프트웨어입니다.
미들웨어는 더욱 빠르게 혁신할 수 있도록 애플리케이션을 지능적이고 효율적으로 연결하는 기능을 제공합니다.
- 데이터베이스 서버에서는 언제나 트랜잭션을 걸 수 있는 상태로 SQL 명령이 실행된다.
- 트랜잭션을 사용할 경우에는 접속형태나 클라이언트 툴의 자동커밋 사용 여부 등 트랜잭션 관련 기능을 파악해 둘 필요가 있다.
DELETE 명령은 삭제 여부에 관해 사용자에게 확인하지 않는다.
- DELETE 명령을 트랜잭션 내에서 실행하는 경우에는 ROLLBACK으로 삭제를 취소할 수 있다.
- 자동커밋으로 되어 있는 경우에는 주의해야 한다.
ROLLBACK으로 취소할 수 있는 것은 트랜잭션 내에서 DELETE 명령을 실행했을 경우만이다.
'책 > SQL 첫걸음' 카테고리의 다른 글
정규화 (0) | 2023.03.12 |
---|---|
복수의 테이블 다루기 (join) (0) | 2023.03.12 |
복수의 테이블 다루기 (집합) (0) | 2023.03.12 |
인덱스(index) (2) | 2023.03.12 |
뷰(view) (0) | 2023.02.24 |