Postgres 1с проверка таблиц на целостность
В Postgres Pro Standard входит утилита pg_integrity_check , предоставляющая следующие возможности для проверки целостности:
Подсчёт и проверка контрольных сумм по требованию
pg_integrity_check может отслеживать контрольные суммы неизменяемых и дополнительных файлов, а также таблиц системных каталогов.
31.2.1.1. Неизменяемые файлы
К отслеживаемым неизменяемым файлам относятся исполняемые файлы, библиотеки и другие файлы, которые никогда не должны изменяться. Контрольные суммы таких файлов определяются в файле конфигурации /opt/pgpro/std-14/share/security/system.conf .
Файл system.conf включён в состав дистрибутива Postgres Pro Standard . Для каждого экземпляра Postgres Pro Standard существует один отдельный файл system.conf . Каждая строка в system.conf соответствует одному отслеживаемому объекту и содержит два поля: контрольную сумму, состоящую из 40 шестнадцатеричных цифр, и относительный путь к файлу. Эти значения разделяются тремя символами: пробел, минус, пробел. Контрольные суммы вычисляются и записываются в этот файл во время установки Postgres Pro Standard . При их расчёте учитывается и содержимое файла, и его атрибуты. Поэтому, например, при изменении прав доступа к файлу его контрольная сумма изменится.
31.2.1.2. Дополнительные файлы
Каждая строка в файле конфигурации соответствует одному отслеживаемому объекту и содержит два поля: контрольную сумму, состоящую из 40 шестнадцатеричных цифр, и относительный путь к файлу. Поля разделяются тремя символами: пробел, минус, пробел.
При расчёте контрольных сумм учитывается и содержимое, и атрибуты файлов. Поэтому, например, при изменении прав доступа к файлу его контрольная сумма изменится.
Чтобы настроить проверку контрольных сумм дополнительных файлов, администратор баз данных должен сделать следующее:
Создать файл конфигурации для каждого кластера, согласно описанному выше соглашению об именовании.
В созданном файле конфигурации перечислить все отслеживаемые дополнительные файлы. В качестве контрольной суммы можно задать любые 40 шестнадцатеричных цифр, например нули.
Примечание
Администратор также может, запустив эту команду, получить примерный файл конфигурации, а затем отредактировать его должным образом.
31.2.1.3. Таблицы системных каталогов
Таблицы системных каталогов представляют собой избранный набор данных, относящихся к экземпляру Postgres Pro Standard . Контрольные суммы таблиц системных каталогов сохраняются в файле конфигурации /opt/pgpro/std-14/share/security/catalog.conf . Проверку целостности таблиц системных каталогов можно настроить только для одной базы данных.
Каждая строка в файле конфигурации соответствует одному отслеживаемому объекту и содержит два поля: контрольную сумму, состоящую из 40 шестнадцатеричных цифр, и относительный путь к файлу. Поля разделяются тремя символами: пробел, минус, пробел.
Чтобы настроить проверку контрольных сумм избранных данных, администратор баз данных должен сделать следующее:
Создать файл конфигурации для выбранной базы данных.
В созданном файле конфигурации перечислить SQL-запросы, которые будут возвращать отслеживаемые данные. В качестве контрольной суммы можно задать любые 40 шестнадцатеричных цифр, например нули.
Примечание
Администратор также может, запустив эту команду, получить примерный файл конфигурации, а затем отредактировать его должным образом.
31.2.2. Проверка целостности при запуске сервера
Контрольные суммы неизменяемых файлов всегда проверяются при запуске сервера Postgres Pro Standard . Если запуск сервера остановлен из-за несовпадения контрольных сумм, администратор должен разобраться в проблеме, разрешить её и перезапустить сервер.
Таблицы системных каталогов и дополнительные файлы при запуске сервера не проверяются. Вы можете проверить их вручную, выполнив pg_integrity_check после запуска сервера.
31.2.3. Планирование проверок целостности
Если вы используете систему семейства Linux, вы можете запланировать периодические проверки целостности, используя демон cron . Для этого измените файл /etc/crontab , добавив в него строки, определяющие частоту запуска утилиты pg_integrity_check . Файл /etc/crontab представляет собой системный файл, содержащий все инструкции для демона cron . Чтобы получить подробное описание формата файла crontab в вашей системе на базе Linux, выполните команду:
Примеры
Следующий пример иллюстрирует организацию проверок целостности в операционной системе Rosa SX:
При нарушении целостности файловой системы сервера баз данных PostgreSQL, последний выдает “Ошибка СУБД” 1С, и часто сопровождается текстом, типа “ERROR: invalid page header in block ХХХХХ of relation base/ХХХХХ/ХХХХХ”.
Причиной подобных исключений может служить разрушенная файловая система и нарушение логической целостности всей базы данных, произошедшие в результате некорректного завершения работы ОС.
Выводимую 1С “Ошибка СУБД” на самом деле надо начинать исправлять не в 1С, а с проверки файловой системы. Полный алгоритм восстановления будет приблизительно следующий:
- Исправление ошибок файловой системы;
- Выявление неисправных таблиц СУБД и их ремонт;
- Проверка и исправление ошибок на уровне 1С в конфигураторе.
Если “Ошибка СУБД” в 1С произошла после некорректного завершения работы ОС, начинаем с команд Chkdsk в Windows и fsck в Linux. Это позволит устранить ошибки на уровне файловой системы.
Затем надо выяснить в каких таблицах БД PostgreSQL возникает ошибка “ERROR: invalid page header in block…”. Для этого обращаемся к логам или пытаемся снять дамп базы данных, например подключившись к СУБД утилитой pgAdmin. Если возникает ошибка “Ошибка СУБД” в 1С, наверняка найдется хотя бы 1 испорченная таблица. В моем случае ошибка возникла при дампе public._enum332.
Для того, чтобы восстановить сломанную таблицу, выполним 3 запроса:
Далее снова пытаемся снять дамп базы данных, пока база не выгрузится без ошибок.
Следующим этапом исправления ошибки СУБД в 1С будет Тестирование и исправление базы в конфигураторе 1С. Для этого запускаем испорченную БД в конфигураторе. Через пункт Администрирование – Тестирование и исправление ИБ пробуем восстановить логическую целостность нашей базы. Обратите внимание, на галочки, выбранные на изображении.
При большом количестве ошибок СУБД, 1С потребуется помощь программиста или грамотного пользователя 1С помимо системного администратора, поэтому будьте готовы к привлечению подобных специалистов.
На этом процедуру исправления ошибки PostgreSQL “ERROR: invalid page header in block…” при работе с 1С можно считать законченной, однако стоит отметить несколько пунктов, которые позволят не допустить возникновение ошибки СУБД в 1С:
Сразу оговорюсь, что мои познания в T-SQL не сильно велики т. к. по большей части пишу код для конфигураций на платформе 1С:Предприятие, и предложенное решение может быть не совсем оптимальным.
Оптимизация и улучшения предложенного скрипта приветствуется.
Небольшое предисловие.
Часто случается, что базы данных повреждаются, по различным причинам, и мы не всегда это вовремя замечаем.
Что бы проверить базу данных надо зайти в интерфейс, запустить скрипт, получить результат. И уже в зависимости от результата принимать какие-то решения и действия. Возможно это нормально, когда есть свободно время и не лень запустить скрипт вручную. Но что делать когда, к примеру, на поддержке с 10-к и более баз и находятся они на разных серверах. Подключаться к каждому серверу и запускать скрипт руками занимает много времени, да делать это вручную лень.
Для разработчика, администратора и т. п. л ень это двигатель его прогресса, настроил систему как надо и читай логи, письма и прочее оповещения.
Вот после очередного повреждения базы, я опять вернулся к задаче проверки целостности баз по регламенту и рассылке результата на почту. Ранее я уже занимался этой задачей но не доделал, точнее не нашел нужного мне решения.
Это было небольшое предисловие, теперь перейдем к самой задаче.
Целью задачи было: проверять целостность баз данных 1с на сервере SQL по регламенту и при обнаружении поврежденной базы оповещать по почте. Оповещение только если найдена поврежденная база. Состав письма краткий, все данные результата проверки высылать не требуется.
Поиски готового решения в интернете ничего не дали. Нашел всего одно решение, но оно мне не подходит. Кому интересно, можете ознакомится с публикацией Отправляем результаты задания DBCC CHECKDB по электронной почте.
На просторах интернета прочитал, что данные можно вывести в таблицу.
DBCC CHCKDB WITH TABLERESULTS выведет данные в таблицу, но просто так взять и сделать выборку из из этой таблицы нельзя, но выход все же нашелся.
В поисках нужной информации для решения моей задачи наткнулся на публикацию Спасибо тебе R odert Pearl , что ты ее когда то написал.
1. Создаем временную таблицу.
Исходное описание таблицы немного изменено.
Добавлена колонка "DatabaseName".
Изменил типы данных в некоторых колонках, т.к. при первом же тесте получил ошибки о невозможности преобразования типов данных
Колонки: PartitionID, AllocUnitID изменил тип данных с INT на BIGINT ,
Колонка: RepairLevel с INT на VARCHAR(300)
В каких колонках нужно менять тип данных искал методом тыка и исключения.
2. В ранее созданную временную таблицу, при помощи CURSOR , по списку баз, поместим выходные данные DBCC CHCKDB .
У меня есть база 'Recovery', использую для разных целей. Сегодя она играет роль поврежденной базы данных. Результ ее проверки и поместим во временную таблицу.
DECLARE @database_name NVARCHAR(50)
DECLARE database_cursor CURSOR FOR
SELECT name
FROM sys.databases db
WHERE name = 'Recovery'
AND db.state_desc = 'ONLINE'
AND source_database_id IS NULL -- REAL DBS ONLY (Not Snapshots)
AND is_read_only = 0
OPEN database_cursor
FETCH NEXT FROM database_cursor INTO @database_name
WHILE @@FETCH_STATUS=0
BEGIN
FETCH NEXT FROM database_cursor INTO @database_name
END
CLOSE database_cursor
DEALLOCATE database_cursor
Теперь с данными можно работать, накладывать отборы, делать сортировку и все остальное.
Мне на выходе нужна одна строка с описанием ошибок. Строку собираю из колонок: DatabaseName , MessageText при помощи конкатенации. Дополнительно накладываю условия на ' MessageText ', что бы получить нужные строки, т.к. если база не повреждена данные в выходном наборе все равно будут. Только в тексте будет количество ошибок "0". Мне эти данные не нужны.
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 10 ошибок согласованности, не связанных ни с одним объектом.
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 30 ошибок согласованности в таблице "_InfoRg23950" (идентификатор объекта 469889041).
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 9 ошибок согласованности в таблице "_Reference12359" (идентификатор объекта 956790716).
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 5 ошибок согласованности в таблице "_InfoRg24673" (идентификатор объекта 1015882886).
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 3 ошибок согласованности в таблице "_InfoRg9101" (идентификатор объекта 1179359466).
DB Recovery: CHECKDB обнаружил 0 ошибок размещения и 57 ошибок согласованности в базе данных "Recovery".
Осталось проверить есть ли у нас в сформированной строке данные, при их наличии отправляем данные на почту.
EXEC msdb.dbo.sp_send_dbmail
@profile_name = @Profilename,
@recipients = @Recipients,
@body = @MSG,
@subject = @Msubject;
END
GO
Проверяем скрипт, все работает.
Создаем Job, настраиваем расписание и готово
DECLARE @database_name NVARCHAR(50)
DECLARE database_cursor CURSOR FOR
SELECT name
FROM sys.databases db
WHERE name = 'Recovery'
AND db.state_desc = 'ONLINE'
AND source_database_id IS NULL -- REAL DBS ONLY (Not Snapshots)
AND is_read_only = 0
OPEN database_cursor
FETCH NEXT FROM database_cursor INTO @database_name
WHILE @@FETCH_STATUS=0
BEGIN
FETCH NEXT FROM database_cursor INTO @database_name
END
CLOSE database_cursor
DEALLOCATE database_cursor
EXEC msdb.dbo.sp_send_dbmail
@profile_name = @Profilename,
@recipients = @Recipients,
@body = @MSG,
@subject = @Msubject;
END
GO
При обновлении базы данных произошел сбой. Не создались таблицы в POstgresql под вновь созданные объекты. В результате при любом обращении к этим объектам вываливалась ошибка типа: "Ошибка СУБД:
ERROR: relation "_infor22964_bydims_rrr" does not exist". Поиски в инете практически ни к чему не привели.
Итак, начнем. Это был ничем не приметный день, кроме того что это был понедельник. По плану было дотянуть до конца рабочего дня и поставить обновление на УПП, в котором должны появиться новый бизнесс процес, константа, и 3 дополнительных регистра сведений. Установку решил проводить "из дома" по удаленномму соединению, т.к. продажники работают до-поздна.
При установке обновления решил не терять времени, поставить обновление конфигурации до того, как все выйдут из базы данных, потом выгнать всех и обновить конфигурацию базы данных. После того, как выгнал пользователей - сделал самый большой прокол в этом дне, последствия которого пришлось разгребать в течении 5-ти часов - не сделал бэкап базы данных.
После обновления базы данных решив заполнить вновь созданные регистры зашел в режим отладки. При открытии формы списка регистра вывалилась ошибка типа "Ошибка СУБД: ERROR: relation "_infor22964_bydims_rrr" does not exist". и предложения: завершить работу и перезапустить.
Первым делом я конечно решил вернуть конфигурацию к первоначальному состоянию. НО в момент обновления конфигурации базы данных вываливалась та же ошибка "типа не найдена таблица и отвали".
Вторым этапом было связаться с администратором сервака и попросить его сделать откат на часик - другой. Одмина пришлось ждать и нервничать ок 2 часов - ибо он ужинал. После окончания ужина узнал, что у него средствами Postgresql делается один архив в сутки, и менно тогда жеж когда у меня делается архив средствами 1С.
Я был практически в отчаинии. Догадывался что работатьна базе можно, но будут проблемы с дальнейшим написанием и обновлением. и с этим надо что-то делать.
Итак в качестве третьего этапа рассматривались следующие варианты: восстановление утреннего архива и перенос документов с помощью типовой обработки "ВыгрузкаЗагрузкаXML", что идет в составе "Конвертации данных" и тестирование и исправление. К тому жеж я задумался над созданием позднего архива. Сразу скажу, что архив не создался, вывалив ту же ошибку.
Вариант с переносом данных решил отложить, ибо "это может быть потраченное впустую время", и ХЗ какой период документов сегодня правила наша "родная" бухгалтерия. И я решил обратиться к просторам инета. Самой полезной инфой было: http://www.forum.mista.ru/topic.php?id=393749&page=1 где мне пришлась по душе идея "исправления таблиц базы данных средствами SQL".
Третий этап, он жеж конечный: "исправления таблиц базы данных средствами SQL".
Теперь расскажу, что мне потребовалось: мне потребовалось сделать восстановление аврхива в базу данных SQL, и установить на компе утилиту "PGAdmin III".
Архивную базу данных я обновил до последнего состояния рабочей базы. Оказалость, что количество таблиц при "нормальном обновлении" на восстановленном архиве на 5 шт. превышало количество таблиц на рабочей базе. из чего я сделал вывод что при обновлении рабочей базы не создалось 5 таблиц. Оставалось найти их и создать вручную. Не смотря на то что на указаном выше форуме прочитал, что при восстановлении базы данных могут создаться таблицы с другими именами, моя практика показала полное совпадение имен рабочей базы и восстановленной. Проблема была в том, что необходимо было найти эти таблицы из 3500 шт. не зная языка SQL.
В итоге, я нашел и создал 5 таблиц недостающих. У меня конфигурация "вернулась в исходное состояние". После этого я сделал архив БД средствами 1С, и повторно выполнил обновление, которое прошло успешно.
Вот так я вышел из сложившегося положения, больше НИКОГДА не буду забывать/забивать делать архив перед обновлением.
Как обнаружить, что база данных повреждена
SQL Server detected a logical consistency-based I/O error: incorrect checksum (expected: 0xfdff74c9; actual: 0xfdff74cb). It occurred during a read of page (1:69965) in database ID 13 at offset 0x0000002229a000 in file 'D:\Develop\Databases\Broken1.mdf'.
Attempt to fetch logical page 1:69965 in database 13 failed. It belongs to allocation unit 72057594049069056 not to 281474980642816.
Что делать если база данных все-таки повреждена
- Не паниковать
- Не отсоединять (detach) ее
- Не перезапускать SQL Server
- Не начинать восстановление сразу
- Запустить проверку целостности
- Найти причину
Не паниковать
Самое важное, при обнаружении повреждения БД — это не паниковать. Любые принимаемые решения должны быть тщательно взвешаны, во внимание должны быть приняты все возможные факторы. Чертовски просто ухудшить ситуацию приняв не до конца обдуманное решение.
Не отсоединять базу данных
В большинстве случаев, когда SQL Server обнарживает повреждение базы данных, это означает, что в БД на самом деле есть поврежденные страницы. Попытка убедить SQL Server что это не так, путем отсоединения (detach) и повторного присоединения (attach) БД, бэкапа и последующего восстановления, перезапуска службы SQL Server, либо перезагрузки сервера, не приведет к тому, что ошибка исчезнет.
Если база данных повреждена и SQL Server обнаружит это при присоединении, он не сможет присоединить ее. Есть несколько способов заставить его увидеть эту БД, но намного лучше просто не отсоединять ее.
Не перезапускать SQL Server
Не начинать восстановление сразу
У вас может возникнуть соблазн просто запустить DBCC CHECKDB с одним из «восстановительных» параметров (обычно допускающими потерю данных) и надеяться, что все станет лучше (по моему опыту — первое что рекомендуют на «непрофильных» форумах по SQL Server — запустить DBCC CHECKDB REPAIR_ALLOW_DATA_LOSS — прим. переводчика). Во многих случаях запуск такого восстановления не рекомендуется. Он не гарантирует исправления всех ошибок и может привести к недопустимой потере данных.
Такое восстановление — это последний шаг при исправлении ошибок. Оно должно быть запущено только если у вас уже нет другого выбора, но никак не в первую очередь.
Запустить проверку целостности
Найти причину
После того как ошибки исправлены, работу нельзя считать законченной. Если причина этих ошибок не установлена, они могут возникнуть снова. Обычно, основной причиной ошибок являются проблемы с подсистемой ввода-вывода, но они также могут быть вызваны неправильной работой «низкоуровнего ПО» (вроде антивируса), действиями человека, либо багами самого SQL Server.
Что дальше
Дальнейшие действия по исправлению ошибок целиком и полностью зависят от результатов выполнения CheckDB. Чуть дальше я покажу несколько наиболее часто возникающих ошибок (учтите, что эта статья не претендует на звание полного описания всевозможных ошибок).
Описанные ошибки располагаются по возрастанию уровня серьезности — от наименее серьезных к наиболее серьезным. В общем-то, для наиболее серьезных ошибок, находимых CheckDB, есть описание доступных методов их резрешения.
Если у вас вдруг обнаружится ошибка не описанная в статье, обратите внимание на последний раздел — «Поиск помощи».
Неверная информация о свободном месте на странице
Msg 2508, Level 16, State 3, Line 1
The In-row data RSVD page count for object «Broken1», index ID 0, partition ID 76911687695381, alloc unit ID 76911687695381 (type In-row data) is incorrect. Run DBCC UPDATEUSAGE.
Msg 8914, Level 16, State 1, Line 1
Incorrect PFS free space information for page (1:26839) in object ID 181575685, index ID 1, partition ID 293374720802816, alloc unit ID 76911687695381 (type LOB data). Expected value 0_PCT_FULL, actual value 100_PCT_FULL.
Эта ошибка появляется, когда PFS-страница (Page Free Space), которая учитывает насколько заполнены страницы в БД, содержит некорректные значения. Эта ошибка, как и упомянутая ранее, не является серьезной. Алгоритм, по которому определялось насколько заполнены страницы, в SQL Server 2000 не всегда отрабатывал правильно. Для решения этой проблемы нужно запустить DBCC CHECKDB с параметром REPAIR_ALLOW_DATA_LOSS и, если это единственная ошибка в БД, никакие данные, на самом деле, не пострадают.
Повреждение только некластерных индексов
Если все ошибки, найденные CheckDB, относятся к индексам с и больше, это означет, что были повреждены только некластерные индексы. Поскольку информация, содержащаяся в некластерных индексах, является «избыточной» (те же самые данные хранятся в куче, либо в кластерном индексе — прим. переводчика), эти повреждения могут быть исправлены без потери каких-либо данных.
Если все ошибки, найденные CheckDB, относятся к некластерным индексам, рекомендуемый «уровень восстановления» для DBCC CHECKDB — REPAIR_REBUILD. Примеры таких ошибок (на самом деле ошибок такого типа намного больше):
Msg 8941, Level 16, State 1, Line 1
Table error: Object ID 181575685, index ID 4, page (3:224866). Test (sorted [i].offset >= PAGEHEADSIZE) failed. Slot 159, offset 0x1 is invalid.
Msg 8942, Level 16, State 1, Line 1
Table error: Object ID 181575685, index ID 4, page (3:224866). Test (sorted[i].offset >= max) failed. Slot 0, offset 0x9f overlaps with the prior row.
В этом случае, повреждение может быть полностью исправлено удалением поврежденных некластерных индексов и повторным их созданием. Перестроение индекса (ALTER INDEX REBUILD) в режиме on-line (и иногда в off-line) читает страницы старого индекса для создания нового и, следовательно, завершится с ошибкой. Поэтому, необходимо удалить старые индексы и создать их заново.
Именно это сделает DBCC CHECKDB с параметром REPAIR_REBUILD, но база данных при этом должна быть в однопользовательском режиме. Вот почему обычно лучше вручную выполнить эти операции, чтобы с базой данных можно было продолжать работать, пока индексы будут пересоздаваться.
Если у вас недостаточно времени на то, чтобы пересоздать нужные индексы и в наличии есть «чистый» (не содержащий в себе ошибок) полный бэкап и бэкапы журнала транзакций с неразорванной цепочкой журналов, вы можете восстановить поврежденные страницы из них.
Повреждение LOB-страниц
Msg 8964, Level 16, State 1, Line 1
Table error: Object ID 181575685, index ID 1, partition ID 72057594145669120, alloc unit ID 72057594087800832 (type LOB data). The off-row data node at page (1:2444050), slot 0, text ID 901891555328 is not referenced.
Ошибка говорит о том, что существуют LOB-страницы (Large OBject), на которые не ссылается ни одна страница с данными. Такое может произойти, если ранее был поврежден кластерный индекс (или куча) и его поврежденные страницы были удалены.
Если CheckDB говорит только о таких ошибках, то можно запускать DBCC CHECKDB с параметром REPAIR_ALLOW_DATA_LOSS — эти страницы будут уничтожены. Поскольку у вас все равно нет страниц с данными, которые ссылаются на эти страницы, бОльшей потери данных уже не будет.
Ошибки, связанные с выходом за пределы допустимого диапазона
Msg 2570, Sev 16, State 3, Line 17
Page (1:1103587), slot 24 in object ID 34, index ID 1, partition ID 281474978938880, alloc unit ID 281474978938880 (type «In-row data»). Column «modified» value is out of range for data type «datetime». Update column to a legal value.
Повреждение кластерного индекса или кучи
Server: Msg 8976, Level 16, State 1, Line 2
Table error: Object ID 181575685, index ID 1, partition ID 76911687695381, alloc unit ID 76911687695381 (type In-row data). Page (1:22417) was not seen in the scan although its parent (1:479) and previous (1:715544) refer to it.
Server: Msg 8939, Level 16, State 1, Line 2
Table error: Object ID 181575685, index ID 0, page (1:168576). Test (m_freeData >= PAGEHEADSIZE && m_freeData
Следует помнить, что если ошибки, возвращаемые CheckDB, относятся к index или 1, это значит, что повреждены непосредственно данные.
Такой тип ошибок исправляется, но исправление заключается в уничтожении строк или целых страниц. Когда CheckDB удаляет данные для исправления ошибки, ограничения, налагаемые внешними ключами, не проверяются и никакие триггеры не срабатывают. Строки или страницы просто удаляются. В результате данные могут оказаться не согласованными, либо может быть нарушена логическая целостность (на LOB-страницы может больше не ссылаться ни одна строка, либо строки некластерного индекса могут указывать «в никуда»). Из-за таких последствий, подобное восстановление, не рекомендуется использовать.
Если у вас есть «чистый» бэкап, восстановление из него обычно является более предпочительным, для исправления таких ошибок. Если база данных находится в полной модели восстановления и у вас есть бэкапы журнала транзакций с неразорванной цепочкой журналов (начиная с последнего «чистого» полного бэкапа), вы можете сделать бэкап активной части лога и восстановить базу данных целиком (или только поврежденные страницы), в результате чего данные вообще не будут потеряны.
Если бэкапа с неповрежденными данными нет, у вас остается только один вариант — запуск DBCC CHECKDB с параметром REPAIR_ALLOW_DATA_LOSS. Это потребует перевода базы данных в однопользовательский режим на все время выполнения этой процедуры.
И хотя у вас нет возможности избежать потери данных, вы можете посмотреть какие данные будут удалены из кластерного индекса. Для этого, посмотрите этот пост Пола Рэнадала.
Повреждение метаданных
Msg 3853, Level 16, State 1, Line 1
Attribute (object_id=181575685) of row (object_id=181575685,column_id=1) in sys.columns does not have a matching row (object_id=181575685) in sys.objects.
Неисправимые повреждения
Повреждение системных таблиц
Msg 7985, Level 16, State 2, Line 1
System table pre-checks: Object ID 4. Could not read and latch page (1:358) with latch type SH.
Check statement terminated due to unrepairable error.
Msg 8921, Level 16, State 1, Line 1
Check terminated. A failure was detected while collecting facts. Possibly tempdb out of space or a system table is inconsistent.
Повреждение «карт распределения»
Msg 8946, Level 16, State 12, Line 1
Table error: Allocation page (1:2264640) has invalid PFS_PAGE page header values. Type is 0. Check type, alloc unit ID and page ID on the page.
Msg 8998, Level 16, State 2, Line 1
Page errors on the GAM, SGAM, or PFS pages prevent allocation integrity checks in database ID 13 pages from (1:2264640) to (1:2272727)
Поиск помощи
Заключение
В этой статье я дал несколько примеров того, что можно сделать при обнаружении поврежденной БД и, что даже важнее, того, что делать не надо. Надеюсь, что теперь вы лучше понимаете какие методы можно применять для решения описанных проблем и насколько важно иметь хорошие бэкапы (и правильно выбрать модель восстановления — прим. переводчика).
Примечание: это мой первый перевод, который, к тому же делался не за раз, а в несколько подходов, вечерами, когда появлялось свободное время, поэтому текст целиком, возможно, кому-то покажется несколько несогласованым. Если где-то я был излишне косноязычен и какая-то часть текста вдруг окажется трудной для понимания — с радостью выслушаю все замечания.
С уважением, unfilled.
P.S. Когда я уже собрался было нажать на кнопочку «Опубликовать», мне на почту свалилась рассылка от SQL Server Central с вот таким вот комиксом.
Читайте также: