거래 격리 수준 스냅 샷 대 절음?


10

SNAPSHOT 격리 대 TRUNCATE와 관련하여 내가 기대하지 않은이 동작에 대해 누군가가 밝힐 수 있기를 바랍니다.

데이터베이스 : 스냅 샷 격리 허용 = True; 커밋 된 읽기 스냅 샷이 켜져 있습니까? = 거짓입니다.

Procedure1 (많은 조인으로 오래 실행되는 복잡한 SELECT에서 테이블 foo의 내용을 대체합니다) :

BEGIN TRAN; 
TRUNCATE TABLE foo; 
INSERT INTO foo SELECT...; 
COMMIT;

Procedure2 (테이블 foo에서 읽음) :

SET TRANSACTION ISOLATION LEVEL SNAPSHOT; 
SELECT * FROM foo;

Procedure2가 실행되는 동안 Procedure1이 실행 중이면 Procedure1이 완료 될 때까지 sp_WhoIsActive에 따라 LCK_M_SCH_S 대기 상태로 Procedure2가 보류됩니다. 그리고 Procedure2가 완료되면이 예외가 발생합니다.

명령문이 액세스 한 오브젝트가이 트랜잭션 시작 이후 다른 동시 트랜잭션의 DDL 문에 의해 수정되었으므로 데이터베이스 'DatabaseName'에서 스냅 샷 격리 트랜잭션이 실패했습니다. 메타 데이터의 버전이 지정되지 않았으므로 허용되지 않습니다. 메타 데이터를 동시에 업데이트하면 스냅 샷 격리와 혼합 된 경우 불일치가 발생할 수 있습니다.

그러나 Microsoft는 SNAPSHOT 격리에서 허용되지 않는 DDL 문으로 TRUNCATE를 표시하지 않습니다. http://msdn.microsoft.com/en-us/library/bb933783.aspx

분명히 TRUNCATE 이전에 테이블에서 가장 최근에 커밋 된 데이터를 즉시 반환하거나 Procedure1에 의해 유지되는 최악의 경우를 반환 한 후 프로 시저 1의 새 내용을 반환 할 것으로 예상되므로 프로 시저 2의 가장 좋은 경우를 예상했을 것입니다. 표. 도울 수 있니?


대신 DELETE FROM foo를 사용할 수 있습니까? 스키마 잠금이 설정되지 않습니다.
SqlACID

DELETE FROM은 실제로이 문제를 해결하는 방법입니다. 또한 오류가 발생하는 이유에 관심이 있습니다 (Procedure1이 반환 된 후에 만).
Mark Freeman

답변:


19

목록 'DDL'에 나열된 작업은 포괄적이지 (그리고 TRUNCATE TABLE그 목록에서 유일한 누락되지 않습니다). 여부는 TRUNCATE TABLEDML또는 DDL논쟁의 양쪽에 설득력있는 사례로, SQL Server에서 고민하는 문제이며, 온라인 설명서의 두 가지 엔트리.

스냅 샷 격리 트랜잭션의 관점에서, 잘라 내기가의 본질적인 품질이 복용하는 Sch-M잠금 차단 설명 (때문에, RCSI그리고 SI여전히 획득의 Sch-S잠금을 ); 또한 내부 메타 데이터 버전 (내부 *)으로 인해 오류 3961이 발생합니다.

따라서, 당신이보고있는 행동은 예상되지만 잘 문서화되지 않았습니다.

* TRUNCATE TABLE의 현재 구현은 행 버전을 생성하지 않습니다. 메타 데이터 버전을 범핑하는 것이 올바른 동작을 보장하는 가장 간단한 방법입니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.