개요
MSSQL에서 스키마를 다량으로 추가/수정하는 쿼리를 테스트하려고 [BEGIN TRAN]-[ROLLBACK TRAN]을 걸고 테스트하는 도중, [ROLLBACK TRAN]이 씹히고 스키마가 모조리 변경되는 대참사가 발생한 이슈가 있어서 기록 및 제대로 이해하려는 목적으로 포스팅을 한다.
GO를 사용하지 않는 트랜잭션
BEGIN TRAN
SELECT @@TRANCOUNT -- : 1
CREATE TABLE [dbo].[TEST1] -- 추후에 롤백됨.
(
[id] INT
);
CREATE TABLE [dbo].[TEST1] -- 중복 생성으로 인한 에러가 발생하고, 트랜잭션이 롤백된 채로 이후 모든 명령어가 무시된다.
(
[id] INT
);
SELECT @@TRANCOUNT -- : 출력되지 않는다.
CREATE TABLE [dbo].[TEST2] -- 생성되지 않는다.
(
[id] INT
);
SELECT @@TRANCOUNT -- : 출력되지 않는다.
ROLLBACK TRAN
GO를 사용하지 않았다면, CREATE TABLE 실패 이후에 트랜잭션이 롤백되어 아무일도 일어나지 않는다.
(CREATE문은 실패하면 XACT_ABORT 설정과 상관 없이 전체 트랜잭션을 롤백한다. 왜 그런지는 못찾겠다 꾀꼬리....)
GO를 사용한 트랜잭션
BEGIN TRAN
SELECT 1, @@TRANCOUNT -- : 1
CREATE TABLE [dbo].[TEST1] -- 추후에 롤백됨.
(
[id] INT
);
GO
CREATE TABLE [dbo].[TEST1] -- 중복 생성으로 인한 에러 발생. (이후, 트랜잭션이 롤백된다.)
(
[id] INT
);
SELECT 2, @@TRANCOUNT -- : 출력되지 않는다.
GO
CREATE TABLE [dbo].[TEST2] -- 생성 성공
(
[id] INT
);
SELECT 3, @@TRANCOUNT -- : 0
GO
ROLLBACK TRAN -- Rollback 할 Tran이 없으므로 에러 발생.
GO문은 만나기 전에 적혀있던 명령어들을 마치 따로 실행시키듯이 분리시키는 명령이다.
그래서 위 쿼리는 아래와 같이 따로 쿼리를 치는 것과 다를바 없이 해석되게 된다.
결론
GO는 아주 편리한 도구이지만 남용하면 대참사를 일으 킬 수 있으니 주의해서 써야 되겠다.
트랜잭션을 걸었다고 생각 없이 쿼리를 막 치지 말자.. 역시 대참사가 발생할 수 있다.
'Programming > MSSQL' 카테고리의 다른 글
MSSQL 특정한 값 제외 평균 (2) | 2023.03.05 |
---|---|
MSSQL 데드락 그래프 (1) | 2023.02.03 |
MSSQL 페이지 위치 쿼리 (0) | 2023.02.02 |
MSSQL 한번에 여러 row 빠르게 넣기 (0) | 2023.02.02 |
MSSQL order by 1 (0) | 2019.10.16 |