Руководство по процессу очистки фантомных записей

Процесс очистки фантомных записей представляет собой однопоточный фоновый процесс, удаляющий записи со страниц, которые были помечены для удаления. В следующей статье приводится обзор этого процесса.

Фантомные записи

Записи, которые удаляются с конечного уровня страницы индексов, физически не удаляются со страницы — запись помечается как подлежащая удалению или фантомная. Это означает, что строка остается на странице, но меняется в строке заголовка, чтобы указать, что она действительно является фантомной. Это позволяет оптимизировать производительность во время операции удаления. Фантомные записи необходимы для блокировки на уровне строк. Они также нужны для изоляции моментального снимка, когда требуется сохранить более старые версии строк.

Задача очистки фантомных записей

Записи, помеченные для удаления (или фантомные), очищаются в ходе фонового процесса очистки фантомных записей. Этот фоновый процесс иногда выполняется после фиксации операции удаления и физически удаляет фантомные записи со страниц. Процесс очистки фантомных записей запускается автоматически через определенный интервал (каждые 5 секунд для SQL Server 2012 и более поздних версий, каждые 10 секунд для SQL Server 2008/2008 R2) и ищет все страницы, помеченные как имеющие фантомные записи. При обнаружении таких страниц процесс удаляет записи, помеченные для удаления (или фантомные), захватывая максимум 10 страниц при каждом выполнении.

Если запись является фантомной, база данных помечается как имеющая фантомные записи и процесс очистки фантомных записей будет проверять только эти базы данных. После удаления всех фантомных записей процесс очистки также пометит базу данных как не имеющую фантомных записей и пропустит ее во время следующего выполнения. Процесс также будет пропускать все базы данных, к которым он не может применить общую блокировку, и повторит попытку во время следующего запуска.

Приведенный ниже запрос позволяет определить количество фантомных записей, существующих в одной базе данных.

SELECT sum(ghost_record_count) total_ghost_records, db_name(database_id) 
FROM sys.dm_db_index_physical_stats (NULL, NULL, NULL, NULL, 'SAMPLED')
group by database_id
order by total_ghost_records desc

Отключение очистки фантомных записей

В системах с высокой нагрузкой и большим количеством операций удаления процесс очистки фантомных записей может вызвать проблемы с производительностью, связанные с сохранением страниц в буферном пуле и созданием операций ввода-вывода. Поэтому этот процесс можно отключить с помощью флага трассировки 661. Однако отключение процесса оказывает влияние на производительность.

Отключение процесса очистки фантомных записей может привести к ненужному увеличению базы данных и возникновению проблем с производительностью. Так как процесс очистки фантомных записей удаляет записи, помеченные как фантомные, после его отключения эти записи будут оставаться на странице и SQL Server не сможет использовать это пространство повторно. В результате SQL Server принудительно добавляет данные на новые страницы, что приводит к чрезмерному увеличению файлов базы данных и может также стать причиной разбиений страниц. Разбиения страниц снижают производительность при создании планов выполнения и проведении операций сканирования.

После отключения процесса очистки фантомных записей необходимо выполнить определенное действие по удалению фантомных записей. Одним вариантом является перестроение индекса для перемещения данных на страницах. Другой вариант заключается в запуске хранимой процедуры sp_clean_db_free_space (для очистки всех файлов базы данных) или sp_clean_db_file_free_space (для очистки одного файла данных базы данных) вручную для удаления фантомных записей.

Предупреждение

Обычно не рекомендуется отключать процесс очистки фантомных записей. Перед окончательным отключением процесса в рабочей среде необходимо провести соответствующую тщательную проверку в управляемой среде.

Далее

Отключение процесса очистки фантомных записей
Удаление фантомных записей из одного файла базы данных
Удаление фантомных записей из всех файлов базы данных