Надежная стратегия резервирования для сохранения данных VLDB.

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

Создание, тестирование и обслуживание рабочего окружения базы данных, для которого любые потери информации и любое время простоя в случае аварии недопустимы, - задача нетривиальная. Что более важно, при планировании обеспечения высокой готовности нужно помнить, что в аварийном состоянии может оказаться не одна только база данных. Многие функции SQL Server - поддержания кластерной отказоустойчивости, журнал транзакций, реплицирование - предполагают высоконадежную реализацию. Однако какой бы уровень надежности ни гарантировало аппаратное обеспечение, всегда должна быть реализована основательная стратегия резервирования. Не имеет значения, с базой данных каких размеров приходится работать или какие требования с точки зрения готовности предъявляются к системе: восстановление - это та процедура, с которой приходится считаться всегда. В ряде случаев, например при непреднамеренном удалении или изменении данных, единственная возможность продолжать работу - восстановить состояние базы данных на момент до внесения изменений.

Стратегия резервирования - основа любого плана восстановления работоспособности после аварии, чем бы она ни была вызвана - случайным удалением данных, аппаратным сбоем, естественной причиной, или каким-либо незапланированным инцидентом. Восстановить данные из резервной копии можно на другие серверы или другие каталоги, разослать копии в географически разнесенные территории по электронной почте или на съемных носителях. Резервное копирование предполагает незначительное расходование денежных средств и немного дополнительного аппаратного обеспечения, за исключением, может быть, самих магнитных носителей информации, лент, например. Вместе с тем, стоит потратить время на изучение всех возможных нештатных ситуаций и убедиться, что процедура резервирования автоматизирована в максимальной для данных условий степени, а восстановление данных произойдет за наименьшее время. При работе с SQL Server 2000 функции резервирования и восстановления легко автоматизируются для реализации гибкого и эффективного плана восстановления после аварии. При этом все возможности резервирования/восстановления включены в состав всех редакций SQL Server 2000 и не требуют наличия версии Enterprise Edition. Более того, на практике дополнительные функции, о которых речь пойдет дальше, помогут минимизировать время простоя и потери данных даже в случае тотального сбоя сервера.

Какую стратегию резервирования выбрать?

На многих промышленных серверах стратегия резервирования и восстановления состоит в периодическом создании полной копии базы данных (например, еженедельно) при дополнительном резервировании журналов транзакций (например, каждый час); в некоторых случаях дополнительно проводится дифференциальное резервирование (differential backups), например каждую ночь за исключением того дня, когда выполняется полное копирование. Такая базовая стратегия вполне приемлема, но использование дифференциального метода снижает возможное время простоя за счет уменьшения объема журналов транзакций, которые необходимо использовать при восстановлении базы данных и приведении ее в рабочее состояние. Нужно восстановить полную резервную копию, самую последнюю дифференциальную копию и журналы транзакций, появившиеся с момента создания дифференциальной резервной копии. Но, так или иначе, обе стратегии предусматривают использование полной резервной копии как начала процесса восстановления базы данных. При работе с очень большой базой данных (very large database - VLDB) сказанное выше означает, что потребуется выделить сотни гигабайт или даже терабайты для обеспечения такой стратегии резервирования. А как долго будет продолжаться процесс резервирования VLDB? И что еще важней - сколько времени понадобится для ее восстановления? Не выйдем ли мы за рамки допустимых ограничений по времени? Если выбранная стратегия не использует вспомогательные приемы, наподобие метода split-mirror, восстановление займет часы. И даже если это допустимо в конкретной организации, сколько данных можно позволить себе потерять? И потом, в чем состоит стратегия избыточности сайта (site redundancy strategy) - в использовании пересылок журнала транзакций (log shipping) или в копировании резервных копий этих журналов на вторичный сайт?

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

Такое развитие событий может показаться невероятным, но если проведение полного резервирования занимает несколько часов, то и риск потерять данные, соответственно, растет. К примеру, если время резервирования составляет 8 часов, то в течение указанного времени вторичный сайт должен работать без единого сбоя, иначе неизбежна потеря данных, изменившихся за эти восемь часов, неважно, по какой причине - из-за незавершенного процесса резервирования или из-за сбоя при копировании данных на вторичный сайт. Потеря данных за 8 часов работы в большинстве случаев недопустима. Но что если резервирование журнала транзакций выполняется во время проведения дифференциального резервирования? Такая методика позволит передать изменения в другой сайт, даже во время резервирования очень большой базы данных. Для того чтобы иметь возможность резервировать журнал транзакций каждую минуту (общая практика при желании свести к минимуму потери данных), администратор может вообще отказаться от полного резервирования базы данных. Используя стратегию резервирования file backup и filegroup backup (файлового и группового резервирования), можно отказаться от проведения полного резервирования базы данных, и резервирование журналов транзакций никогда не будет приостанавливаться. Такая стратегия позволяет иметь на вторичном сайте данные с минимально возможным отставанием от главного сайта и минимизировать вероятные потери данных.

Некоторые базовые стратегии резервирования и восстановления данных имеют ряд ограничений. Задание на полное резервирование может быть запущено в любое время и здесь нет реальных ограничений. Однако при выполнении более специфических стратегий файлового и группового резервирования необходимо соблюдать требования, в которых нужно разбираться. Главное, резервирование журнала транзакций должно выполняться регулярно. Копия журнала транзакций - это критический компонент при восстановлении базы данных, и он необходим для процедуры восстановления при использовании стратегии файлового и группового резервирования. Чтобы приступить к резервированию журнала транзакций и, следовательно, минимизировать потери данных, в первую очередь необходимо установить модель восстановления базы данных или в состояние Full или в Bulk_logged. Поскольку модель восстановления Simple не позволяет резервировать журнал транзакций, она не может использоваться в сочетании с файловой и групповой стратегией резервирования.

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

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

Для тех таблиц, характер использования которых различен, нужно применять различные группы файлов для каждого типа данных. Например, создание четырех групп файлов - одна для данных "только чтение", одна для данных "чтение-запись", одна для текстовых данных и изображений и одна для очень больших таблиц - поможет при выборе стратегии резервирования. Создаются не только менее крупные таблицы (разделы), что позволит ускорить их обработку, дополнительно будут задействованы новые возможности при проведении резервирования и, что особенно важно, при восстановлении, а это сократит время простоя и затраты на резервирование. Для того чтобы определиться с нужным числом групп файлов и файлов для базы данных, нужно ясно представлять себе эти данные. В предлагаемой врезке "Использование групп файлов при работе с VLDB" даются соответствующие рекомендации.

Резервирование как пошаговый процесс

Когда проект проработан и установлена модель восстановления Full (или Bulk_logged), можно воспользоваться преимуществами выбранной стратегии резервирования. Для демонстрации синтаксиса и возможностей файлового и группового резервирования обратимся к Рисунку 1.

Чтобы создать базу данных PubsTest и выполнить все имеющиеся в нашем примере задания на резервирование, нужно запустить сценарий FileFilegroupStrategiesCaseStudy.sql. Сценарий может быть выполнен "как есть", но я рекомендую внимательно изучить синтаксис предлагаемого сценария и разобраться в стратегии резервирования.

В предлагаемом сценарии задействовано семь файлов: основной файл, три файла в группе файлов под названием RWFG (используется для чтения и записи данных), два файла в группе файлов ROFG (только для чтения данных), а также журнал транзакций. После создания базы данных PubsTest сценарий модифицирует данные в промежутке между сеансами резервирования. На диаграмме перечисляются типы заданий на резервирование слева направо в определенной последовательности (номер типа задания соответствует номеру на временной шкале):

  1. Задание Full file backup основного файла

  2. Резервирование файла журнала транзакций

  3. Задание Full filegroup backup для группы RWFG

  4. Резервирование файла журнала транзакций

  5. Задание Full filegroup backup для группы ROFG

  6. Резервирование файла журнала транзакций

  7. Задание Differential filegroup backup для группы RWFG

  8. Резервирование файла журнала транзакций

  9. Задание Full file backup основного файла

  10. Резервирование файла журнала транзакций

  11. Задание Differential filegroup backup для группы RWFG

  12. Резервирование файла журнала транзакций

  13. Заключительное резервирование файла журнала транзакций после разрушения базы данных.

Обратите внимание, что на временной шкале под номером 13 находится задание на резервирование после сбоя системы. Когда состояние базы данных - suspect, прежде всего следует понять, можете ли вы зарезервировать оставшийся журнал транзакций. Данные в журнале транзакций отражают последнюю минуту работы базы, что даст возможность восстановить ее, опираясь на результаты самого последнего задания на резервирование, непосредственно перед сбоем. Для резервирования остатков журнала транзакций следует использовать инструкцию BACKUP LOG с параметром NO_TRUNCATE.

Когда применяется файловая и групповая стратегия резервирования, необходимо убедиться, что резервируется каждый файл, чтобы в наличии всегда был полный backup-набор (т.е. все файлы базы данных) и всегда будет возможность заново сформировать рабочее окружение и саму базу данных, если в том будет необходимость. Backup-набор может быть создан или путем резервирования каждого отдельного файла, или используя задание на резервирование группы файлов, или комбинируя оба подхода. В SQL Server 2000 есть возможность резервировать все файлы по отдельности - даже если они являются членами одной и той же группы. В SQL Server 7.0 можно резервировать только целиком всю группу файлов; нельзя создать резервную копию отдельно взятых файлов, если они являются членами группы файлов. Обозначенное изменение в версии SQL Server 2000 позволяет в большей степени использовать возможности резервирования и восстановления данных: если возникает изолированный сбой, достаточно будет восстановить только один пропущенный файл. Однако поиск нужных страниц в огромном хранилище группового резервирования займет больше времени, чем восстановление этого файла из индивидуальной резервной файловой копии.

Из приведенного примера с PubsTest видно, что база данных обеспечена самой последней резервной копией основного файла (задание 9) и резервными копиями групп файлов (задание 3 и 5). В число возможных сценариев восстановления входит восстановление всей базы данных целиком. Однако одно из наиболее ценных приобретений от использования стратегии файлового и группового резервирования - возможность быстрого восстановления в случае сбоя носителя или изолированной порчи данных. Вместо того чтобы заново восстанавливать всю базу данных целиком или запускать частичное восстановление базы из полной резервной копии (что займет еще больше времени, поскольку резервная копия содержит всю базу, а не какой-то отдельно взятый файл или группу файлов), появляется возможность адресного восстановления испорченного файла или группы файлов. Чтобы выработать правильную стратегию восстановления после изолированного сбоя, следует прочесть врезку "Восстановление данных после изолированного сбоя на диске". В статье содержится синтаксис, примеры и некоторые важные рекомендации.

Чтобы восстановить целую базу PubsTest, нужно построить ее каркас (database framework), после чего в первую очередь восстанавливаются самые последние резервные копии отдельных файлов и групп файлов. Чтобы построить пример каркаса, следует восстановить резервное задание под номером 9 для создания основного файла (primary file), затем - под номером 3 для формирования группы файлов RWFG, и, наконец, необходимо восстановить резервную копию под номером 5 для получения группы файлов ROFG. Поскольку процесс восстановления базы данных еще не завершен (все файлы базы данных находятся в разных состояниях и для восстановления работоспособности нуждаются в повторе всех завершенных транзакций до непротиворечивого состояния данных), база данных сообщает, что находится в состоянии загрузки (loading). Чтобы можно было продолжать использование журналов транзакций (для приведения всех файлов базы данных к одной и той же временной отметке), при восстановлении всех файлов и групп файлов используется режим NORECOVERY. Этот режим позволяет восстанавливать резервные копии без перевода базы в рабочее состояние до тех пор, пока она не будет восстановлена полностью. Когда все будет готово для переключения базы данных в это состояние, используйте следующую инструкцию:

RESTORE DATABASE dbname WITH RECOVERY

А пока придется повторять все транзакции, постепенно приближаясь к моменту возникновения сбоя. Для минимизации времени повторного выполнения транзакций в дополнение к резервированию журналов транзакций можно создавать дифференциальные резервные копии. Это можно делать на любом уровне: базы данных, файла, группы файлов. Следующий шаг на пути восстановления - восстановление самой последней дифференциальной копии всех файлов и групп файлов. В рассматриваемом примере у нас имеется дифференциальная копия RWFG под номером 7 и она же под номером 11. Поскольку дифференциальные копии содержат все изменения с момента последнего полного копирования файла или группы файлов, достаточно восстановить только копию под номером 11. Если при восстановлении данной дифференциальной копии возникает сбой, всегда можно воспользоваться следующей по времени дифференциальной копией. Таким образом, получается, что выбранная стратегия резервирования обладает некоторой избыточностью, что немаловажно.

Наконец, база данных наполнена некоторым содержимым. Однако она все еще не готова к восстановлению. Файлы по-прежнему находятся на разной стадии модификации: основной файл в состоянии номер 9, RWFG - номер 11, а ROFG - номер 5. Следующий шаг заключается в корректном повторении транзакций из набора резервных копий. Чтобы определить правильную последовательность повторения транзакций, сначала необходимо отыскать самый старый резервный набор, который предстоит восстанавливать. В нашем случае восстановление должно происходить в следующем порядке:

  1. Восстанавливается резервная копия под номером 9 для получения самой поздней версии основного файла;

  2. Восстанавливается резервная копия под номером 3 для получения самой поздней версии группы файлов rwfg;

  3. Восстанавливается резервная копия под номером 5 для получения самой поздней версии группы файлов rofg;

  4. Восстанавливается резервная копия под номером 11 для получения самой поздней дифференциальной версии группы файлов rwfg.

К этому моменту группа файлов ROFG по времени отстает больше всего - она соответствует номеру 5. Чтобы восстановить ее на момент времени за минуту до сбоя, необходимо рассчитать минимальный номер копии журнала транзакций для повторения. Для этого следует использовать предысторию резервного копирования. Запрос msdb по истории резервных копий способен ускорить процесс расчета; однако база msdb во время выполнения процедуры восстановления после сбоя может оказаться недоступной. Если же база msdb доступна, следует выполнить запрос на получение информации о резервных копиях базы данных. Данные об истории резервирования базы данных, полученные из msdb, могут снабдить полной информацией, поскольку SQL Server автоматически не удаляет историю резервного копирования из системной базы msdb. Исторические данные хранятся постоянно. При желании можно периодически очищать msdb от устаревшей информации, но на всякий случай стоит убедиться, что имеется, по крайней мере, две полные копии базы msdb. Чтобы удалить сведения об истории резервного копирования, воспользуйтесь процедурами msdb.dbo.sp_delete_database_backuphistory или msdb.dbo.sp_delete_backuphistory (соответствующие параметры и синтаксис описаны в SQL Server 2000 Books Online - BOL).

Если база msdb недоступна, необходимые сведения об истории резервирования могут быть получены непосредственно из заголовка резервного устройства. Для этого используется указание LOAD HEADERONLY. В Web-Листинге 1 показано, как применяется это синтаксис. При использовании LOAD HEADERONLY требуется, чтобы устройство резервирования было включено. Нужно подключить все устройства резервирования, подготовить к работе, запустить сценарий и собрать все необходимые данные, хотя, возможно, время выполнения процедуры восстановления из-за этого заметно возрастет (скорее всего, несколько раз будет установлена не та лента, и правильная последовательность загрузки наборов резервного копирования будет нарушена). Важно обеспечить постоянную готовность msdb для организации подобных мероприятий; во врезке "Msdb. Полезные советы" даны рекомендации по переустановке msdb, чтобы задания резервного копирования журнала транзакций могли нормально завершаться и запускаться столько раз, сколько необходимо.

Изучая пример с PubsTest, рекомендую обратить внимание на информацию о проведении резервного копирования, которую можно получить с помощью запроса, представленного в Листинге 1. Результаты выполнения запроса показаны в Таблице 1. Эти результаты абсолютно понятны, так как при проведении резервного копирования используется удобное соглашение об именах. Я рекомендую всегда применять некий стандартный подход при именовании заданий резервного копирования и использовать описания последних, чтобы в дальнейшем можно было без труда отыскать правильную последовательность резервных копий для восстановления после аварии. В данном примере с базы данных PubsTest были использованы имена, говорящие сами за себя, такие как PubsTest Backup, File = pubs, поэтому поле описания самого задания осталось пустым. Кроме того, в целях обучения перед запуском процедур резервного копирования все предыдущие записи были удалены.

Итак, каркас базы данных восстановлен, и мы знаем, что группа файлов ROFG имеет статус самого раннего объекта во всем наборе резервного копирования базы. Для восстановления состояния базы до момента времени, отстоящего от аварии на одну минуту, необходимо в правильной последовательности восстановить журналы транзакций. Для этого следует отыскать минимальный эффективный номер LSN пятого задания в колонке First_LSN Таблицы 1. В нашем случае минимальный эффективный LSN задания на резервное копирование под номером 5 - это 13000000248600001. Чтобы узнать, какие журналы транзакций восстанавливать, следует найти журнал транзакций, чей минимальный эффективный LSN меньше, чем указанный номер - в нашем случае это задание на резервное копирование под номером 6. Теперь нужно найти следующий LSN с еще меньшим значением, поскольку ведется поиск того журнала транзакций (или нескольких журналов), в котором (или которых) содержится транзакционная информация о том, что происходит за время выполнения резервного копирования. Так как резервирование журналов транзакций, файлов и групп файлов может осуществляться конкурентно, за короткий промежуток времени может появиться множество копий журналов, какого-то большого файла или группы файлов. В ряде случаев самый первый журнал транзакций для загрузки оказывается "моложе" загружаемого файла или группы файлов. Поэтому нужно всегда просматривать последовательные номера журналов транзакций и проверять, правильно ли выбрана отправная точка.

Для завершения полного восстановления базы данных необходимо повторить все транзакции, начиная с резервной копии под номером 6. В нашем случае нужно восстановить копию 6, затем 8, 10, 12 и, наконец, 13 - тогда временная отметка состояния базы будет соответствовать моменту аварии с точностью до одной минуты. Для резервной копии под номером 13 (самый последний журнал транзакций) можно применить параметр RESTORE WITH RECOVERY для перевода базы данных в рабочее состояние или параметр NORECOVERY, после чего использовать инструкцию RESTORE DATABASE PubsTest WITH RECOVERY для завершения восстановления базы данных.

Будьте во всеоружии

Восстановление базы данных в полном объеме из резервных копий файла и групп файлов - это наиболее сложная стратегия резервирования и восстановления. Данная стратегия требует проведения очень большого числа тестов, приобретения практических навыков, например, в части организации и именовании заданий резервного копирования msdb для облегчения дальнейшего восстановления данных. Но, применяя эту стратегию, можно полностью восстановить базу данных, даже не выполняя предварительно ее полного копирования и не приостанавливая заданий на резервирование журналов транзакций. Следуя этой стратегии, можно выбрать время проведения резервирования тех частей базы, к которым осуществляется обращение только на чтение данных, и тем самым сэкономить время резервирования и средства, затрачиваемые на магнитные носители. Кроме того, поскольку работа с журналом транзакций никогда не останавливается, вторичные сайты (например, промежуточные сайты транзакций) всегда будут получать журналы транзакций настолько быстро, насколько это вообще возможно. Это значительно сократит потери данных в случае сбоя.

Кимберли Трипп - президент компании SYSolutions. Она имеет сертификат MCT и более чем 10-летний опыт решения реальных проблем в и с помощью SQL Server. С ней можно связаться по адресу: Kimberly@SolidQualityLearning.com. Web-сайт: http://www.SQLSkills.com.