기존 테이블이 있습니다.
CREATE TABLE dbo.ProofDetails
(
ProofDetailsID int NOT NULL
CONSTRAINT PK_ProofDetails
PRIMARY KEY CLUSTERED IDENTITY(1,1)
, ProofID int NULL
, IDShownToUser int NULL
, UserViewedDetails bit NOT NULL
CONSTRAINT DF_ProofDetails_UserViewedDetails
DEFAULT ((0))
);
이 테이블에는 150,000,000 개의 행이 있습니다. 시스템이 연중 무휴 운영되므로 정기적으로 발생하는 유지 관리 기간이 없습니다.
테이블에 인덱스를 추가하고 싶습니다. Enterprise 버전의 SQL Server에서는 테이블에 대한 쓰기 액세스를 차단하지 않고이를 수행 할 수 있어야합니다. 내가 사용한 명령은 다음과 같습니다.
CREATE INDEX IX_ProofDetails_ProofID_Etc
ON dbo.ProofDetails (ProofID, IDShownToUser)
INCLUDE (UserViewedDetails)
WITH (ONLINE=ON
, ALLOW_ROW_LOCKS=ON
, ALLOW_PAGE_LOCKS=ON
, FILLFACTOR=100
, MAXDOP=4
);
SSMS에서을 눌러 명령문을 자체적으로 실행했습니다 F5. 1 분 이상 실행 된 후 다른 세션을 차단하기 시작했습니다. 그런 다음 CREATE INDEX
다른 세션을 차단할 수 없으므로 명령 을 즉시 취소했습니다 .
첫 1 분 동안 내 CREATE INDEX
명령 을 막는 것이 아무것도 없었으며 sys.dm_exec_requests
대기 유형으로 프로세스를 보여주었습니다 CXPACKET
. 나는 작업이 병렬화 된 이후로 이것이 나쁜 것이라고 생각하지 않습니다.
의 출력을 검사 할 시간이 많지 않았습니다 sys.dm_exec_requests
. 쿼리에서 하나의 행만 반환되었습니다 WHERE session_id = xxx
. 차단 된 세션이 대상 테이블에 행을 삽입하려고했습니다.
명령문이 시작된 후 약 2 분 후에 명령문 실행을 취소 한 것을 제외하고는 잠금이 얼마나 오래 지속되었는지 알 수 없습니다. 그 시점에서 약 1 분 동안 블록이 발생했습니다.
구현을 오해하고 WITH (ONLINE=ON)
있습니까? 아니면 내가 알아야 할 다른 것이 있습니까?
서버는 2 개의 쿼드 코어 Xeon E5-2643 3.3Ghz 프로세서, 192GB RAM 및 5,000 개 이상의 iops를 지원하는 SAN 스토리지를 갖춘 상당히 견고한 시스템입니다. CPU는 일반적으로 20 % 미만, RAM은 93 %, 주로 SQL Server에서 사용됩니다. 기본적으로 Windows Server 2012 및 SQL Server 2012 만 실행됩니다.
답변
online = on으로 인덱스를 생성 할 때 인덱스 생성 프로세스는 인덱스 객체 자체를 생성 할 때 차단되지 않지만 프로세스가 거의 끝날 때 실제로주기 위해 일정 기간 동안 스키마 수정 잠금 *을 획득합니다. 인덱스를 테이블에 추가하면이 잠금 유형은 잠금이 해제 될 때까지 모든 외부 작업을 차단하므로 차단 문제가 발생할 수 있습니다.
* Sch-M
다른 모든 경우에 필요하지만 새로운 비 클러스터형 인덱스의 온라인 빌드 에는 잠금이 필요하지 않습니다. 새로운 비 클러스터형 인덱스에는 준비 단계에서 필요한 것과 마찬가지로 최종 단계에서 테이블 수준 공유 잠금 만 필요합니다.
자세한 내용은이 백서를 참조하십시오.
질문에 대한 의견에서 Mushtaq Mohammed 가 제안한대로 다음을 참조하십시오.
유니콘, 무지개, 온라인 인덱스 작업 에 의해 폴 랜달