프로젝트/데이터베이스

MS-SQL에서 (NOLOCK) 이란?(트랜젝션 격리 수준)

쿠키담임선생님 2022. 12. 20. 09:50

기본설명


MS-SQL 을 보다 보면 테이블 명 뒤에 (NOLOCK)을 적어주는 경우를 확인할 수 있다.

 

해당 이유는 MS-SQL의 기본 격리수준이 Read Committed 이기 때문이다. 

 

이 뜻은 한 A라는 테이블을 조회 할 경우 이 A 라는 테이블에 대해 'Insert', 'Update', 'delete' 등이 발생한 후 조회가 가능하다는 뜻이다.

 

이를 방지하기 위해 테이블 명 뒤에 NOLOCK을 적을 수 있는데 이를 사용하면 Read Uncommitted 와 같아진다.

 

이 뜻은 테이블이 작업 중(잠겨있음)이어도 기다리지 않고 조회(더티 리드) 하겠다는 뜻이다.

장점은 이를 통해 조회 성능이 올라가고, 데드락을 방지 할 수 있다.

단점은 커밋되지 않은(수정 전) 데이터를 읽기 때문에 트랜잭션이 롤백될 경우 잘못된 데이터를 읽을 수 있다.

즉 (NOLOCK)은 정확성이 필요한 경우에는 사용하지 말아야한다.

 

NOLOCK 없는 SELECT


만약 음식이라는 테이블이 있고, 치킨 가격을 5000원에서 10000원으로 업데이트를 햇다고 가정하자.

UPDATE price

SET food_price = 10000

WHERE food_id = 'chicken'

이렇게 될 경우 새로운 쿼리창에서 select 시 위 쿼리가 완료될 때 까지 select 작업은 대기(suspend) 상태가 된다.

 

NOLOCK 있는 SELECT


UPDATE price

SET food_price = 10000

WHERE food_id = 'chicken'

이렇게 될 경우 SELECT 를 하면 해당 업데이트 내용으로 조회가 된다.

 

여기서 주의해야 할 점은 만약 해당 쿼리가 'ROLLBACK'이 일어날 경우 롤백을 못시킨다는 것이다.

 

그러므로 정확성이 필요할 경우는 NOLOCK을 사용해서는 안된다.

 

반대의 경우 - SELECT 중 해당 테이블을 변경하려고 하는경우


조회 중에도 정상적으로 UPDATE 된다.

SELECT 를 사용 시 공유잠금이 걸리게 되는데

공유 잠금은 SELECT 작업이 수행되는 즉시 해제되기 때문에 트랜잭션이 종료되지 않아도 UPDATE가 가능하다.