COMM UNCOMMITTED 격리 수준을 사용하는 최상의 상황


10

우리 모두 알고 있듯이, READ UNCOMMITTED는 더티 읽기 및 팬텀 읽기와 같은 것들이 발생할 수있는 가장 낮은 격리 수준입니다. 이 격리 수준을 사용하기 가장 좋은시기는 언제이며 어떤 이유로 사용해야합니까?

실제로 나는 이전에 답변을 읽었지만 충분한 예가 없기 때문에 완전히 이해할 수 없었습니다.

답변:


20

내가 사용 READ_UNCOMMITTED(또는 NOLOCK)하지만 일상적으로 응용 프로그램 코드에서 SSMS에서 생산 데이터베이스를 쿼리 할 때. 이 연습 (MAXDOP 1 쿼리 힌트와 함께)은 데이터 분석 및 문제 해결을위한 일반적인 쿼리가 프로덕션 워크로드에 영향을 미치지 않도록하며 결과가 올바르지 않을 수 있음을 이해합니다.

슬프게도, 나는 참조 READ_UNCOMMITTED/ NOLOCK데이터 무결성의 비용으로 막지 않도록 생산 코드에 널리 사용. 적절한 솔루션은 행 버전 격리 수준입니다 ( SNAPSHOT또는 READ_COMMITTEDREAD_COMMITTED_SNAPSHOT데이터베이스 옵션 ON쿼리 및 인덱스 튜닝) 및 / 또는주의.

나는 최근에 코드가 NOLOCK때로는 잘못된 결과를 반환했기 때문에 유일한 변경 사항을 제거하는 proc을 검토했습니다 . 제거 NOLOCK는 좋은 것이었지만 누락되거나 중복 된 행이 일반적으로 큰 테이블의 할당 순서 스캔 중에 발생한다는 것을 알고 UNION ALL효율적인 인덱스 사용을 촉진 하는 기술을 사용하도록 리팩토링을 제안했습니다 . 이제 쿼리는 몇 밀리 초 안에 실행되어 모든 세계에서 가장 좋은 올바른 결과를 얻습니다.


7

나는 당신이 결과를 받아들이고 다른 옵션이 없다면 어떤 상황에서는 괜찮다고 생각합니다 .

다른 옵션의 경우, 새로운 애플리케이션에는 RCSI (Read Committed Snapshot Isolation)를 사용하거나 RCSI에서는 경쟁 조건에 대한 전체 코드베이스를 쉽게 테스트 할 수없는 구형 애플리케이션에는 SNAPSHOT ISOLATION (SI)을 사용하도록 사람들을 강요했습니다.

그러나 이는 적합하지 않을 수 있습니다. tempdb를 사랑하고 돌보는 데 약간의 시간이 더 필요할 수 있으며, 아무도 버전 트랜잭션 (및 tempdb)이 디스크를 확장하고 채우도록하는 열린 트랜잭션을 떠나지 않도록해야합니다.

DBA가 없거나 SQL Server를 모니터링하고 관리하는 사람이 있다면 이러한 옵션이 위험 할 수 있습니다. 보다 일반적으로, 모든 사람이 서버로가는 코드를 완전히 제어 할 수있는 것은 아니며, 여기서는 연결 문자열이나 코드를 변경하여 SI에 문제 쿼리를 요청할 수 있습니다.

게다가 대부분의 사람들은 전체 응용 프로그램에 잠금 문제가 없습니다 . OLTP 데이터보고와 같은 문제가 있습니다. 작성자가 차단하지 않은 보고서와 교환하여 NOLOCK / RU의 상충 관계를 수용 할 수있는 경우이를 수행하십시오.

그 의미를 이해해야합니다. 그것은 당신의 쿼리 가 어떤 잠금도 취하지 않는다는 것을 의미 하지 않으며, 그것은 다른 쿼리에 의해 취해진 잠금을 존중하지 않는다는 것을 의미합니다.

물론 문제가 라이터 / 라이터 잠금 인 경우 도움이되는 유일한 옵션은 SI이지만 오류 처리 등으로 올바르게 구현하려면 엄청난 양의 개발자 작업이 필요합니다.


5
그리고 문제가 실제로 OLTP 데이터에 대한보고 인 경우,이를 일종의 읽기 전용 보조 (AG, 로그 전달, 복제 또는 롤-오브-롤)로 오프로드하십시오.
Aaron Bertrand

3
@AaronBertrand 그리고 그들은 모니터 할 두 번째 서버를 가질 것입니다 ;)
Erik Darling

5

IMHO 현대 시스템에서 READ UNCOMMITTED 의 유일하게 유효한 유스 케이스는 개발중인 세션을 다른 세션에서 디버깅 할 때 이므로 저장된 proc이 계속 실행되는 동안 수행중인 작업을 볼 수 있습니다. 프로덕션 시스템에서는 일반적으로 사용되지 않습니다. 약간의 성능 향상이있을 수 있지만 장기적으로는 가치가 없습니다.


3

우리는 항상 건강 관리에 사용합니다.

개별 데이터 행이 쿼리 도중 변경되는 것은 매우 드문 일이며 읽기 / 쓰기 비율은 10,000 / 1과 비슷하며 대부분은 업데이트가 아닌 삽입입니다. 예를 들어, 실험실 인터페이스가 환자의 실험실 결과를 데이터베이스에 쓸 때 해당 값은 변경되지 않습니다.

데이터 변경되면 한 번에 한 행씩 변경됩니다. 아무도 전체 열을 업데이트하지 않습니다 (DBA를 제외하고는 실제로 나쁜 결과를 낳을 때).

다른 한편으로, 우리는 72 시간 이내에 응급실로 돌아 오는 환자와 같은 것을 스캔하기 위해 많은 쿼리를 실행하여 테이블을 완전히 망치게합니다.

10 년 동안의 건강 관리 SQL에서 본 적이 없습니다 Rollback Transaction. 최종 사용자 경험을 방해하지 않고 출입하고 싶습니다. OLTP 데이터베이스 속도를 늦출 위험이 있고 나쁜 데이터를 가져올 위험이 적다면 NOLOCK을 사용합니다.

해야 우리는 그것을 사용합니까? 그럴 수도 있고 아닐 수도 있고. 일반적으로 말하면, 내가 작업 한 많은 응용 프로그램 데이터베이스가 잘 설계되었다고 말하지는 않습니다. 그들은 일반적으로 안티 패턴으로 가득 차 있습니다.


4
참고로 nolock으로 부분적으로 작성된 행을 읽을 수 있습니다.
Max Vernon

1
돈! 이 물건을 배송 할 수 있도록 상사에게 다른 서버를 사달라고해야합니다 ..
James

3
커밋되지 않은 읽기, 특히 "손상된 데이터 읽기"섹션에 대한 Paul White의이 멋진 블로그 게시물에 관심이있을 수 있습니다. 커밋되지 않은 읽기 격리 수준
Josh Darnell

1

READ_UNCOMMITTED/NOLOCK데이터의 정확성이 실제로 주요 목표가 아닌 경우 좋은 옵션입니다. 때로는 대략적인 집계 수가 필요한 경우가 있습니다. 예 : INSERT 또는 UPDATE 테이블에 사용되는 저장 프로 시저가 있습니다. 때로는 업데이트 또는 삽입 할 레코드 수가 너무 많습니다 (수천 개의 레코드). 이러한 저장 프로 시저가 실행되는 동안 NOLOCK대상 테이블에서 간단한 선택 쿼리를 정기적으로 실행하여 원활하게 진행되는지 확인할 수 있습니다 (업데이트 쿼리의 경우 업데이트되는 레코드의 상태 변경 열이있는 경우 해당 열을 사용하여 group by쿼리 를 실행할 수 있음) NOLOCK상태 변경 횟수가 지속적으로 변경되는지 확인).


0

COMMUNCOMMITTED는 읽기만하는 것이 아니라 추가적인 일관성 문제를 야기합니다. 액세스 방법에 따라 행이 누락되거나 동일한 행을 두 번 이상 읽을 수도 있습니다. 세부 사항에 관심이 있다면 Itzik Ben-Gan의 기사를 읽으십시오.


3
기본 읽기 커밋 된 수준에서도 행이 누락되고 행을 두 번 이상 읽을 수 있습니다. 스캔 중에 인덱스 키 열이 업데이트되어 이동하는 경우.
마틴 스미스

이 답변에 대한 사이드 토론이 채팅 으로 이동 되었습니다 .
Paul White 9
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.