반응형
반응형

앞에서 인덱스 조각화 확인 방법을 소개하였으므로, 이제는 인덱스 조각화를 제거하는 방법을 설명하겠습니다. 인덱스 조각화를 제거하는 방법에는 여러 가지가 있습니다. 인덱스를 재구성하거나 인덱스를 재작성하거나 인덱스를 삭제하고 다시 만드는 등의 여러 가지 방법이 가능합니다. SQL Server 2005에서 인덱스 조각화 제거 구문에 변경이 발생하였으므로, 이미 아시는 내용이겠지만 기본적인 내용을 살펴 보겠습니다.  

인덱스 다시 구성

 

ALTER INDEX 문에 REORGANIZE 절을 사용하면 인덱스를 다시 구성할 있습니다. SQL Server 2000에서의 DBCC INDEXDEFRAG 대신 기능을 사용하는 것을 권고합니다.

인덱스를 다시 구성하면 리프 노드의 논리적 순서(왼쪽에서 오른쪽으로) 일치하도록 리프 수준 페이지가 다시 정렬되어 테이블과 뷰의 클러스터형 비클러스터형 인덱스의 리프 수준이 조각 모음됩니다. 클러스터형 인덱스를 다시 구성하면 클러스터형 인덱스의 리프 수준에 포함된 모든 LOB 열이 압축됩니다. 비클러스터형 인덱스를 다시 구성하면 인덱스 내의 포괄 열인 모든 LOB 열이 압축됩니다.

sys.indexes 카탈로그 뷰의 채우기 비율 값을 기준으로 인덱스의 페이지를 압축하고, 압축으로 인해 생성된 페이지는 제거됩니다. 재구성은 온라인으로 수행되며, 차단 잠금을 오래 보유하지 않으므로 쿼리나 업데이트의 실행을 차단하지 않습니다.

인덱스가 심하게 조각화되지 않은 경우에는 인덱스를 재구성하면 되지만, 인덱스가 심하게 조각화된 경우에는 인덱스를 재작성하는 것이 좋습니다..

 

인덱스 재구성하기

USE AdventureWorks;

GO

ALTER INDEX PK_ProductPhoto_ProductPhotoID ON Production.ProductPhoto

REORGANIZE ;

GO

 

 

인덱스 다시 작성

 

인덱스 조각화로 인한 성능 저하를 방지하기 위해서는 주기적으로 인덱스 조각화가 진행된 테이블들에 대한 조각화 제거 작업이 필요합니다. 조각화를 제거하기 위한 작업 중의 하나가 인덱스를 다시 작성하는 것입니다. 인덱스 재작성은 인덱스를 삭제한 다시 생성하는 작업으로, 인덱스를 논리적 정렬과 일치하도록 물리적으로 재정렬합니다. 인덱스가 만들어졌을 지정된 FILLFACTOR 계산하여 인덱스의 페이지를 압축하여, 디스크 공간을 확보하고 필요한 만큼 페이지를 할당하여 인덱스 행을 연속되는 페이지에 다시 정렬합니다. 작업은 ALTER INDEX REBUILD 절을 사용하여 있으며, DBCC DBREINDEX 대신 기능을 사용하는 것을 권고합니다. 또한, CREATE INDEX DROP_EXISTING 절을 사용하여 인덱스 재작성 작업을 수도 있습니다. 작업을 통하여, 요청한 데이터를 얻는 필요한 페이지 읽기 횟수를 줄일 있으므로 디스크 성능이 향상됩니다.  ALL 명시하면 하나의 트랜잭션으로 테이블의 모든 인덱스를 제거하고 다시 작성합니다. SQL Server 2005에서는 비클러스터형 인덱스를 온라인으로 재작성할 있습니다.

가능한 인덱스 재작성 작업을 자동화하여 주기적으로 용이하게 수행할 있는 체계를 갖출 것을 권고합니다.

 

비클러스터형 인덱스를 온라인 모드로 재작성하기

ALTER INDEX IX_Employee_ManagerID ON HumanResources.Employee

REBUILD WITH (ONLINE=ON);

GO

 

반응형
반응형

인덱스는 검색의 속도를 빠르게 해 주는 매우 유용한 기능입니다. 초보 DBA들의 경우에는 인덱스는 한번 만들어 두기만 하면 되는 것으로 알고, 인덱스에 대한 관리를 전혀 하지 않는 경우들이 흔히 있습니다. 수년동안 사용해 오면서 재구성 작업을 한번도 실행해 주지 않아서 인덱스 조각화가 매우 심해진 경우들도 심심찮게 볼 수 있습니다. 인덱스 조각화가 매우 심한 경우에 인덱스 재구성만으로도 성능이 개선되는 효과를 얻기도 합니다. 이와 같이 인덱스는 주기적인 관리가 필요한데, 그런 관리를 위해서는 인덱스의 조각화가 어느 정도 진행되었는지를 확인하는 방법을 알고 있어야 합니다. 그래서 오늘은 먼저 인덱스 조각화를 확인하는 방법에 대하여 소개해 보겠습니다. 


테이블에 INSERT, UPDATE, DELETE가 발생함에 따라서 조각화가 발생하게 됩니다.
조각화가 발생하면 원하는 데이터를 가져오기 위하여 읽어야 페이지 수가 늘어나, 성능에 좋지 않은 영향을 미칠 있으므로 주기적으로 조각화를 제거하는 작업이 필요합니다. 인덱스 관리에 대하여 알고 있는 DBA들은 주기적으로 인덱스 조각화 제거를 위한 인덱스 재구성 작업을 실행해 줍니다. 그런데 대부분의 경우에 특정 데이터베이스 내의 모든 사용자 테이블들의 모든 인덱스들에 대하여 한번에 인덱스 재구성을 수행하는 것이 일반적입니다. 시스템 오픈 초기에는 데이터의 크기가 작아서 속편하게 한달에 한번 또는 일주일에 한번 야간에 인덱스 재구성을 수행하여도 문제가 없었는데, 데이터의 크기가 점점 커져서 어느 날에는 야간 업무 휴지 시간동안 인덱스 재구성 작업이 완료되지 않아서 정상적인 서비스를 제공하지 못하는 장애가 발생하는 경우도 가끔 볼 수 있습니다.
인덱스 조각화 정도는 인덱스에 따라 천차만별인데 무조건 일률적으로 인덱스 조각화 제거 주기를 적용하는 것은 비효율적이라고 생각합니다. 그러므로 먼저 인덱스 별로 인덱스 조각화 상태를 모니터링하고, 인덱스 별로 인덱스 재구성 스케줄을 적절하게 구성하는 것을 권고합니다. 그리고 향후 소요시간이 증가할 경우를 대비하여 인덱스 별로 날짜를 분산하여 인덱스 재구성을 실행할 것을 권고합니다.


그러면 이제 본론으로 들어 가서 인덱스 조각화를 확인하는 방법을 설명하겠습니다. 

조각화 정보를 알기 위하여 이전 버전에서 사용했던 DBCC SHOWCONTIG 사용이 가능하지만, SQL Server 2005에서는 테이블의 조각화 정보를 sys.dm_db_index_physical_stats 동적 관린 뷰를 사용하여 확인할 있습니다.

 

[구문]

sys.dm_db_index_physical_stats (

    { database_id | NULL }               /* NULL: 서버내의 모든 데이터베이스 */

    , { object_id | NULL }                /* NULL: 해당 데이터베이스내의 모든 오브젝트 */

    , { index_id | NULL | 0 }              /* NULL: 해당 테이블의 모든 인덱스 */

    , { partition_number | NULL } /* NULL: 해당 오브젝트의 모든 인덱스 */

    , { mode | NULL | DEFAULT } /* NULL: LIMIT */

)

mode에는 DEFAULT, NULL, LIMITED, SAMPLED, DETAILED 입력할 있으며, DEFAULT 또는 NULL LIMITED 의미합니다.

LIMITED 모드는 가장 빠르고 가장 적은 페이지를 스캔합니다. , 힙의 모든 페이지와 인덱스의 레벨을 제외한 페이지를 스캔합니다.

SAMPLED 모드는 인덱스 또는 힙의 모든 페이지중에서 1% 샘플에 대한 통계를 반환합니다. 만일, 인덱스 또는 힙이 10,000 페이지보다 적다면 SAMPLED 대신에 DETAILED 모드가 사용됩니다.

DETAILED 모드는 모든 페이지를 스캔하고 모든 통계를 반환합니다.


조각화는 다음과 같은 스크립트를 활용하여 확인 가능합니다.

DECLARE @db_id SMALLINT;

DECLARE @object_id INT;

 

SET @db_id = DB_ID(N'AdventureWorks');

SET @object_id = OBJECT_ID(N'AdventureWorks.Person.Address');

 

IF @db_id IS NULL

BEGIN;

    PRINT N'Invalid database';

END;

ELSE IF @object_id IS NULL

BEGIN;

    PRINT N'Invalid object';

END;

ELSE

BEGIN;

    SELECT * FROM sys.dm_db_index_physical_stats(@db_id, @object_id, NULL, NULL , 'LIMITED');

END;

GO
반응형

+ Recent posts

반응형