Резервное копирование БД
Введение
Любому системному администратору и\или программисту известна аксиома "бэкапов мало не бывает". Среди администраторов также ходит слух "системные администраторы делятся на тех кто делает быкапы и на тех кто их будет делать". Могу сказать, что постоянная тяга делать бэкапы перед любым изменением в системе, иногда даже и без изменений, например проснувшись посреди ночи в холодном поту, признак того что it-специалист достиг первой ступени просветления. Достигнуть можно двумя путями: простой - поверить что без этого никак и сразу начать их делать, посложней - наступить на избитые грабли, надеяться на надежное оборудование и ответственных пользователей, ни то ни другое не дает и 90%, что и приведет вас сначала к феерическому провалу... затем наступит просветление - бэкапить и еще раз бэкапить, днем и ночью.
backup - в переводе с англ. "резервная копия", это файл который позволяет развернуть копию базы на определенный момент времени, суть - сжатая архиватором копия "рабочего" файла базы данных.
Зачем нужен бэкап
- Основное назначение: восстановление базы в случае поломки сервера с базой или повреждения каким либо способом рабочего файла базы.
- Вспомогательное назначение: разворачивать копии, иногда восстанавливать данные некоторых таблиц, в случае если затерли какие-то данные, как обычно "нечаянно"... Признаться в случае с 1С, вариант замены базы из бэкапа ради восстановления одной таблицы, практически не используется, в силу того что "поезд ушел", вернете старую версию - добавится работа по восстановлению документов которые уже успели наколотить, поэтому чаще поднимают копию и тянут данные из нее через COM или какую-нибудь самописную выгрузку.
Как правило, для бэкапов выделяют отдельное файловое хранилище, может быть отдельный диск на этом же сервере (не рекомендуется), отдельный сервер с диском, или просто внешний жесткий диск. В крупных компаниях для этих целей закупают аппаратные устройства хранения, целые дисковые массивы и специальное ПО, которое пишет данные на эти диски.
В компаниях поменьше это обычные сервера, на которые добавили побольше дисков или один-два внешних HDD.
Общее правило для бэкапов - не хранить их на том же сервере что и базы данных, ну на крайний случай там же, но диск физически должен быть другим, иначе грош цена такому бэкапу, который ломается одновременно с базой.
Как сделать бэкап
Первым делом смотрим где у нас хранятся данные. В случае с 1С это может быть два варианта:
- База файловая: данные хранятся в каталоге, нам нужен файл "*.1CD", который и содержит все данные.
- База серверная: база подключена через сервер 1С:Предприятия, сами данные хранятся на сервере СУБД (например MSSQL), файлы там тоже есть, но прямого доступа к ним мы не имеем.
В случае с MSSQL файл БД имеет расширение "*.mdf", а где хранится физически - можно узнать или специальной командой к серверу СУБД или в свойствах базы через консоль управления MSSQL, впрочем файлы СУБД нам и не нужны.
В зависимости от того какая база выбираем один из вариантов:
- Файловый вариант базы:
- Вариант первый копирование файла БД:
- Отключаем пользователей от базы (ночью можно и не отключать, также имейте ввиду что вариант не дает 100% рабочий бэкап, в случае когда с базой активно работают).
- Копируем файл 1Cv8.1CD в любую папку
- Сжимаем полученную копию архиватором
- Перемещаем архив в хранилище бэкапов
- Второй вариант через конфигуратор***:
- Открываем базу в режиме "конфигуратор"
- Выбираем в меню "Администрирование → Выгрузить информационную базу"
- Перемещаем полученный файл *.dt в хранилище бэкапов. Файл dt уже сжат, поэтому архиватор тут не нужен.
- Вариант первый копирование файла БД:
- Серверный вариант базы (сторонняя СУБД):
- Специальной командой заставляем сервер СУБД "отдать" нам резервную копию файла БД в файл ХХХХХ.bak (стандартное расширение для бэкапов MSSQL "bak").
- Сжимаем полученную копию архиватором. В новых версиях MSSQL, можно установить сжатие в момент создания файла bak (рекомендуется!), поэтому этот шаг можно пропустить.
- Перемещаем архив в хранилище бэкапов. В новых верстиях MSSQL можно как место сохранения сразу указать сетевой каталог (рекомендуется!), поэтому этот шаг можно пропустить.
*** Рекомендуемый разработчиком и надежный способ для файлового варианта. Этот способ используется чаще для переноса данных из файлового варианта в серверный, можно использовать для бэкапа мелких баз, крупные таким методом бэкапить проблематично. Способ подходит для файлового и серверного варианта.
Особенность любой системы резервного копирования это запуск по расписанию. Для файлового варианта все пункты могут быть выполнены специальными программами, коих немало (например Cobian Backup), или своим скриптом в планировщике (мне ближе этот метод), а в серверном варианте команду резервного копирования запускаем через "планы обслуживания" сервера MSSQL.
Настройка бэкапов MSSQL
- Открываем MSSQL Server Management Studio
- Создаем новый план обслуживания → Правой на узел "Планы обслуживания" → Создать план
- Добавляем графический блок резервного копирования (перетягиваем мышью "задачу" из панели слева)
- Двойным кликом по рамке задачи открываем ее, заполняем свойства:
- Выбираем базы которые должны сохраняться
- Устанавливаем флаг сжатия баз. Внимание! Это значительно снижает трафик и занимаемое место!
- Выбираем каталог хранения бэкапов. Советую указывать сразу сетевой путь, хранилище бэкапов.
- По желанию настраиваем логирование процесса (кнопку см. на рис. выше), у меня лог сохраняется в папку, а также приходит письмо на эл. почту. Если надо отправлять письмо, то надо настроить соответствующий компонент и создать предварительно одного оператора.
- Готово. Проверку работоспособности выполняем так: правой на план → выполнить. После выполнения плана: смотрим лог выполнения, понятно файлы которые появились в хранилище, а также историю (правой на план → история).
- Проверка. Обязательно хотя бы один раз проверить работоспособность резервной копии. Как сделать: создаем новую пустую базу, правой на базу → ... → восстановить, в качестве источника задаем сетевой путь к нашему файлу ХХХХХ.bak (можно скопировать путь из проводника), меняем в параметрах целевой файл (по умолчанию MSSQL попытается заменить рабочую базу) на файлы вашей новой копии - восстанавливаем в копию. На сервере 1С:Предприятие создаете новую базу "копия01", указываете, как источник, свою свежую копию на сервере SQL. Затем заходите в созданную копию через 1С, и проверяете что все на месте и работает.
Настройка бэкапов в файловом варианте базы
- Создаем скрипт который будет выполнять копирование файла 1CD, его сжатие и копирование архива в хранилище. Вот пример такого скрипта:
On Error Resume Next 'внимание! эту строку закомментировать на время отладки! '************************************************* 'Блок переменных '************************************************* 'Класс, описывающий свойства базы 1С class Base1C Dim BaseName 'Имя базы Dim BasePath 'Путь к базе данных 1С (каталог без \ на конце) End class Dim BasesList() 'Массив всех баз Dim MyBase Dim LogStream Const LogPath = "\\server1\logs\log_backups.log" 'путь к лог-файлу Const TempPath = "\\server1\temp_folder_backups" 'временный каталог Const BackupsPath = "\\server2\backup\FILE_BASE" 'каталог хранилище бэкапов Const RarPath = "C:\Program Files (x86)\AutoBackups\Rar.exe" 'путь к архиватору Const BlatPath = "C:\Program Files (x86)\AutoBackups\blat.exe" 'путь к программе отправки сообщений Set objFSO = CreateObject("Scripting.FileSystemObject") Set LogStream = objFSO.OpenTextFile(LogPath, 8, True) ReDim BasesList(0) '************************************************* 'Блок заполнения списка баз '************************************************* '_______________ 'server server1 AddBase BasesList, "BP_base1", "\\server1\1C\BP_base1" AddBase BasesList, "BP_base2", "\\server1\1C\BP_base2" '_______________ 'server server3 AddBase BasesList, "BASE3", "\\server3\bases\BASE3" '************************************************* 'Основной функционал '************************************************* '_______________ PrintToLog "Начало операции резервного копирования баз 1С", true, true For I = 0 To UBound(BasesList)-1 Set MyBase = BasesList(I) PrintToLog CStr(I) & ". Добавление в архив базы " & MyBase.BaseName & ", путь: " & MyBase.BasePath, false, true FilesList = CopyFilesBase(MyBase.BasePath,MyBase.BaseName) AddToArhive FilesList, MyBase.BaseName 'WScript.echo "был: "+CStr(I)+" \ "+CStr(UBound(BasesList))+", "+MyBase.BaseName Next SendMail() LogStream.Close Function SendMail() dim Comand,t_subject,t_body 'blat -body "TEST" -to test@yandex.ru -server smtp.mail.ru -f test@mail.ru -u test@mail.ru -pw пароль Set WshShell = WScript.CreateObject("WScript.Shell") t_subject = "Backups 1c bases 1CD "+CStr(Now) t_body = t_subject Comand = Chr(34)+BlatPath+Chr(34) +" -body "+Chr(34)+t_body+Chr(34)+" -subject "+Chr(34)+t_subject+Chr(34)+" -to mailXXXX@yandex.ru -server smtp.yandex.ru -port 25 -f mailXXXX@yandex.ru -u mailXXXX@yandex.ru -pw pasXXXX"+" -attach "+LogPath WshShell.Run Comand End Function Sub AddToArhive(FilesList, BaseName) dim NewFileName, Comand, I Set WshShell = WScript.CreateObject("WScript.Shell") 'WSHell.Run "7z a -tzip D:\backup\1C\1SBDB\rab"+daydate+".zip -r e:\base\1cv77\1sbdb\* -x!*.cdx", 2, true For I = 0 To UBound(FilesList)-1 FileName = FilesList(I) 'содержит копии файлов которые надо архивировать NewFileName = BackupsPath & "\" & BaseName & "_backup_" & Date & ".rar" Comand = Chr(34)+RarPath+Chr(34) +" m "+NewFileName+" -m1 -ep -rr "+FileName 'команда архивирования с удалением исходного файла PrintToLog Comand, false, true WshShell.Run Comand, 1, 1 Next End Sub Function CopyFilesBase(Folder,BaseName) Dim NewFileName Dim FilesList() ReDim FilesList(0) Set ResFSO = CreateObject("Scripting.FileSystemObject") Set ResFolder = ResFSO.GetFolder(Folder) For Each File In ResFolder.Files if File.Name = "1Cv8.1CD" or File.Name = "1cv8ddb.1CD" then NewFileName = "" & TempPath & "\" & BaseName & "_" & File.Name ResFSO.CopyFile Folder & "\" & File.Name, NewFileName ReDim Preserve FilesList(UBound(FilesList)+1) FilesList(UBound(FilesList)-1) = NewFileName end if Next CopyFilesBase = FilesList End Function Sub AddBase(BasesList,Name,Path) Set MyBase = New Base1C ReDim Preserve BasesList(UBound(BasesList)+1) MyBase.BaseName = Name MyBase.BasePath = Path Set BasesList(UBound(BasesList)-1) = MyBase Set MyBase = Nothing End Sub Sub PrintToLog(StrLog,AddSep,AssTime) if AddSep=true then LogStream.WriteLine "=============" end if Str = "" if AssTime=true then Str = ""&Time&": " end if Str = Str&StrLog LogStream.WriteLine Str End Sub
- Все что нужно сделать - сохранить этот листинг в текстовый файл с расширением .vbs, заполнить переменные вверху скрипта своими данными (путь к логу, хранилищу ...), а также заполнить список баз, указав пути к своим базам. Далее добавить скрипт в планировщик windows, как правило еженощное выполнение.
- Готово. Ждем первого запуска, для теста можно запустить задачу вручную - правой - выполнить.
- Скрипт и вспомогательные утилиты можно скачать по ссылке.
Заключение
По MSSQL: в статье рассмотрен только вариант "полной" резервной копии. Для экономии места занимаемого бэкапами используют "разностные" копии (только изменения) и другие варианты, но в этом случае присутствуют свои заморочки с восстановлением - требуется не один файл бэкапа, а несколько.
Есть еще один нюанс, начинающие программисты постоянно борются с файлом журнала транзакций, который разрастается и забивает диски. Мой совет - если с SQL на "Вы" поставьте для базы "модель восстановления" в ее параметрах в "простая", тогда журнал транзакций будет использоваться по минимуму и не будет расти.
По файловому варианту БД: скрипт легко можно допилить на удаление старых копий, чтобы не держать заведомо устаревшие и потому бесполезные файлы. Можно добавить его же копию в другую задачу, но с периодичностью в месяц и указать другое хранилище, где будут храниться бэкапы раз в месяц. Наконец можно, вместо копирования и архивирования, указать команду запуска 1С и сохранения через конфигуратор бэкапа *.dt (см. запуск 1С в пакетном режиме).