Операция «ALTER INDEX ALL REBUILD» в SQL Server 2012 завершилась неудачно, поскольку в журнале транзакций не хватило места. Индексы никогда не реорганизовывались и не перестраивались, поэтому фрагментация составляет более 80% почти по всем из них.
БД использует простую модель восстановления. Я предполагал, что после каждой операции с индексом, выполняемой формой «ВСЕ» команды, данные журнала транзакций будут сбрасываться до следующей перестройки индекса. Так ли это на самом деле, или перестройки индекса записываются так, как будто они являются частью одной транзакции?
Другими словами, могу ли я уменьшить рост журнала транзакций, написав скрипт для выполнения каждой перестройки в отдельности? Есть ли другие факторы, которые следует учитывать?
sql-server
index
Google Fail
источник
источник
Ответы:
1) Очистка журнала: модель восстановления ПРОСТА не очищает журнал после каждой транзакции, но на контрольных точках. ( ссылка для получения дополнительной информации)
2a) REBUILD ALL: да, REBUILD ALL работает как одна транзакция. Перестройки индекса внутри имеют свои собственные транзакции, но общая операция не завершена до конца. Так что да, вы можете ограничить рост файла журнала, перестраивая отдельные индексы (и, возможно, выполняя команды CHECKPOINT).
2б) Доказательство! Здесь есть демо-скрипт. (Построен в 2016 г.) Сначала создайте тестовую базу данных с таблицей и индексами:
Теперь вы можете сравнить активность журнала между REBUILD ALL и индивидуальной перестройкой
Обратите внимание, что первая открытая транзакция (идентификатор транзакции 0000: 000002fa для меня) не фиксируется до конца REBUILD ALL, но для перестроений с индексом по индексу они фиксируются последовательно.
источник
В настоящее время это единственная транзакция.
источник
Вопрос тривиален для восстановления в автономном режиме . Конечно, это одна транзакция. Представьте себе хаос, который может произойти, если операция разделит каждый индекс на свою собственную транзакцию, так как ей придется снять блокировки при фиксации, а затем повторно получить их. Хотя блокировка критической таблицы SCH-M была снята, индексы могут быть отброшены и могут быть созданы новые индексы, как оператор будет обрабатывать такие случаи? Не говоря уже о том, что таблица может быть удалена и даже воссоздана между двумя транзакциями! Включая случай, когда таблица удаляется и создается другая таблица с тем же идентификатором объекта (да, это может произойти) ...
Что, если вы добавите вопрос, чтобы сказать, что произойдет, если перестроение индекса будет перестроено онлайн ? Это одна транзакция или много? Ответ сложен, поскольку в действительности задействовано несколько внутренних транзакций . Тем не менее, ключевым моментом является то, что существует общая транзакция архивирования, которая охватывает всю операцию (оператор ALTER), и это закрепляет журнал на месте (не может усекаться), таким образом, необходимо соответствующим образом запланировать операцию, чтобы обеспечить ~ 1.6x данные размер для режима полного восстановления или 0,2-кратный размер данных для режима BULK_LOGGED / SIMPLE. Смотрите связанные бумаги для более подробной информации.
Вы можете утверждать, что почему автономная сборка не использует те же внутренние транзакции, что и онлайн-режим, и не разделяет операцию? Проблемы, которые я упомянул о том, что таблица изменяется / удаляется между отдельными индексными операциями (т. Е. Таблица «стабильность схемы»), по-прежнему требуют наличия всеобъемлющей транзакции, которая содержит SCH-S в таблице на протяжении всей продолжительности оператора. Поскольку эта транзакция должна содержать SCH-S также во время восстановления, она должна быть записана в журнал, и как таковая будет запись журнала BEGIN XACT, которая закрепит журнал и предотвратит усечение в течение всей продолжительности оператора. Я знаю, что эта конкретная проблема решалась в период времени SQL 2016-2017 (из-за проблем с размером журнала SQL Azure),
но я не уверен, какой прогресс был достигнут. Похоже, в предварительном просмотре:Возобновляемое восстановление индекса в открытом доступе для SQL Server 2017 CTP 2.0 .источник
Да, у меня была такая же проблема с очень большим столом. Всякий раз, когда я запускал ALTER INDEX ALL, журнал транзакций сильно увеличивался, но если бы он выдавал ALTER INDEX индивидуально, использование пространства журнала было бы меньше.
источник
Предыдущий ответ Remus о том, что для онлайн-индексации требуется 1,6-кратный размер индекса в режиме полного восстановления, неверен. Доля пространства журналирования транзакций, необходимая для перестроения индекса онлайн в режиме FULL, может быть намного выше, и мы неоднократно наблюдали размер индекса, особенно когда перестраиваемый индекс сжимается, поскольку журналирование транзакций не сжимается. Уже одно это должно прояснить, что регистрация транзакций во время онлайн-перестроения под FULL может по крайней мере в несколько раз превышать размер индекса. Добавьте в служебную запись записи журнала, которая не полностью документирована Microsoft, но часто оценивается в 60 байт на строку, и пропорциональный размер ведения журнала при перестроении индекса в режиме онлайн при полном восстановлении может во много раз превышать размер перестраиваемого индекса, особенно если индекс сжат
источник
Rdfozz верен, это лучший способ решить, можно ли перестроить ваш самый большой индекс на основе текущего хранилища. Просто запустите,
dm_exec_requests
пока происходит операция (или SQL Profiler), чтобы увидеть, перестраиваются ли все индексы. Я также хотел бы рассмотреть вопрос об изменении модели восстановления для массовой регистрации. Это то, что я делаю, и в окне все еще есть резервная копия журнала транзакций. См. Ниже статью https://technet.microsoft.com/en-us/library/ms191484(v=sql.105).aspxисточник