webew
Войти » Регистрация
 
PHP
MySQL/MariaDB

Живой бэкап сайта

12 октября 2008, 17:29

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

Предлагаем следующий алгоритм действий:

  • Ежедневно в 5 утра, cron на сервере www запускает скрипт ~/backup.pl, который выполняет следующий ряд действий:
    • Создает дамп базы и архив каталога htdocs.
    • Копирует дамп и архив на backup-сервер.
    • Запускает на backup-сервере скрипт ~/store_backup.pl, который выполняет следующие дествия:
      • Удаляет каталог htdocs и пересоздает пустую базу данных.
      • Разархивирует архив файлов и восстанавливает базу данных из дампа.
      • Добавляет информацию в .htaccess для того, чтобы backup-версия была доступна только по паролю.
      • Совершает иные действия, требуемые для работоспособности перенесенного сайта.
      • Создает каталог с именем, совпадающим с текущей датой и в него переносит новые backup-файлы.
      • Удаляет старые backup-файлы (сохраняются последние 20).

В результате живого бэкапа, на резервном сервере всегда будет работоспособная версия сайта. Заказчик сможет проверять, что backup действительно существует и работает и это придаст ему спокойствие и уверенность в качестве услуг. По датам сообщений на сайте будет видно, что резервная копия сделана сегодня в 5 утра.

Пример

В качестве примера рассмотрим бэкап сайта webew.ru.

Пусть у нас есть два сервера: основной (www) и резервный (backup). На каждом сервере настроен apache, на первом на адрес webew.ru, на втором на адрес backup.webew.ru. На каждом сервере есть пользователь webew, база данных webew, а корневой каталог сайта — каталог htdocs в домашнем каталоге пользователя webew. Пусть также пользователь webew@www может подключаться по ssh к серверу backup без пароля (с использованием ключа, если эта тема интересна — напишу отдельную статью). Кроме того, для удобства поместим имя и пароль для доступа к базе данных в файл .my.cnf в домашнем каталоге пользователя на каждом из серверов.

crontab на www:

[webew@www ~]$ crontab -l
0      5       *       *       *       ~/backup.pl

Скрипт ~/backup.pl на сервере www (прошу прощения за ломаный перл):

#!/usr/bin/perl

$dbname = 'webew';
print "Start backup.\nmysqldump...";
print `mysqldump -R $dbname > $dbname.sql`;
print "bzip2...";
print `rm $dbname.sql.bz2`;
print `bzip2 $dbname.sql`;
print "done\ntar...";
print `tar cfj $dbname.tbz2 htdocs`;
print "done\nscp...";
print `scp $dbname.tbz2 $dbname.sql.bz2 webew\@backup.webew.ru:`;
print "done\nstore backup...\n";
print `ssh webew\@backup.webew.ru "./store_backup.pl"`;
print "fin";

Скрипт ~/store_backup.pl на сервере backup:

#!/usr/bin/perl

$dirbase = "backup";
$dbname = "webew";

if( (!-f "$dbname.tbz2") || (!-f "$dbname.sql.bz2") ) {
    print "No new backup found\n";
    exit;
}
print "Start storing backup\n";

my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime time;
$mon++;
if($mon<10) { $mon = "0$mon"; }
if($mday<10) { $mday= "0$mday"; }
$year=$year-100;
if($year<10) { $year = "0$year"; }

$dirname = $dirbase . "/" . $year . $mon . $mday;
print `mkdir -p $dirname`;
print "$dirname/ \n";

print "untar...";
print `rm -rf htdocs`;
print `tar xfj $dbname.tbz2`;
print `cat .htaccess.add >> htdocs/.htaccess`;
print "done\nmysql...";
print `echo "DROP DATABASE IF EXISTS $dbname" | mysql test`;
print `echo "CREATE DATABASE $dbname CHARSET UTF8" | mysql test`;
print "cleared...";
print `bunzip2 -c $dbname.sql.bz2 | mysql $dbname`;
print "done\n";
print `mv $dbname.tbz2 $dbname.sql.bz2 $dirname/`;

print "remove old...";
$count = 20; # keep this number of backups
print `LANG=C cd $dirbase && ls -t | awk '{i=i+1;if(i>$count) print \$1}' | xargs rm -rf`;
print "done\n";

print "\nfin\n";

~/.htaccess_add на backup:

AuthType Basic
AuthName webew
AuthUserFile /home/webew/.htpasswd
require valid-user

Файл ~/.my.cnf на обоих серверах:

[client]
user=webewdbuser
password=webewdbpassword

Файл .htpasswd создан shell-командой:

htpasswd -c .htpasswd username

Если вы опасаетесь взлома основного сервера, то процедуру можно обратить: скрипт ./store_backup на backup-сервере будет подключаться к основному серверу, создавать на нем копию данных и копировать ее себе. В таком случае злоумышленник, получивший доступ к основному серверу не сможет получить ssh-доступ к резервному.

Заключение

Живой бэкап позволяет заказчику быть уверенным, что резервная копия действительно есть. Кроме живого бэкапа, не забывайте сохранять копии проектов на локальной машине и на сменных физических носителях.


© Все права на данную статью принадлежат порталу webew.ru. Перепечатка в интернет-изданиях разрешается только с указанием автора и прямой ссылки на оригинальную статью. Перепечатка в печатных изданиях допускается только с разрешения редакции.
Добавить комментарий
Отображение комментариев: Древовидное | Плоское
NO USERPIC

poison

А не проще использовать, к примеру, rsync? Резервный сервер находится в "теплом" состоянии. Т.е. MySQL и Apache не запущены. Синхронизируется директория htdocs и data (в которой хранятся базы данных). При необходимости запускаем Apache и MySQL и получаем рабочую копию сервера. Заодно решается проблема, когда бекапить надо кучу сайтов.

Правда, данный подход можно использовать только когда имеется полный контроль над сервером (т.е. используется либо собственное железо, либо виртуальный выделенный сервер).
12.10.2008, 19:47
Ответить
NO USERPIC

rgbeast

rsync для htdocs поможет съэкономить трафик, но для баз данных это не лучший способ. В случае Innodb, mysqldump --single-transaction --master-data=2 позволит получить самосолгасованный бэкап файлов (и согласованный с бинлогом). Копирование файлов базы при том, что основной сервер работает, с большой вероятностью приведет к битым таблицам.

Оптимальный вариант: rsync + репликация базы данных, но в этом случае проверить работоспособность сайта-копии будет невозможно, так как это нарушит репликацию.
12.10.2008, 20:03
Ответить
NO USERPIC

poison

Согласен, что базы лучше делать через mysqldump. Если бинарики таблиц напрямую копировать будут траблы.
А с какой целью проверять работоспособность бекапа сайта (ов)? Ведь это только усложняет задачу, причем, не совсем обоснованно.
12.10.2008, 23:37
Ответить
NO USERPIC

rgbeast

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

Теперь, пусть я заказчик. Я знаю, что есть дамп. Но можно ли его будет восстановить или нет? Трудно сказать глядя на дамп, не тестируя его. Предложенный подход автоматизирует тестирование. Если загружается главная страница сайта, то это очень хороший тест всех аспектов корректности дампа. Кроме того, по главной странице видно является ли дамп актуальным. Предложенный подход - это, фактически, автоматизация процесса тестирования восстанавливаемости бэкапа.
13.10.2008, 00:06
Ответить

bur

А по статистике, какие происшествия чаще всего случаются с сервером и чего стоит опасаться?
Поясню свой вопрос.
Предположим, на моем VDS у меня есть проект projectname.ru и я решил сделать его резервную копию на backup.projectname.ru на том же VDS. Всё отлично работает, но в один не прекрасный день на сервере сыпется хард и я теряю как основную версию сайта, так и бекап. Собственно всё :-)
Чего стоит опасаться и как можно автоматизировать перенос бекапа на другие хосты?

----
Кстати, статья, имхо, заслуживает метки Perl, про PHP в ней ни слова :-)
А можно решить такую задачу средствами PHP + system ?
13.10.2008, 11:32
Ответить
NO USERPIC

rgbeast

Наиболее частое происшествие - разрушение жесткого диска. Нет смысла живой backup делать на том же сервере. Например, рассмотренный в примере сайт webew переносится на backup.webew.ru, размещенный на отдельном георгафически удаленном VDS.

Еще причины:
- случайно стерты данные (неосторожность админа, взлом хакерами или некорректность скрипта)
- хостер не отвечает на звонки, сервер не в сети

К PHP статья относится, так как сайт, резервная копия которого делается, обычно написан на PHP :)

К Perl, напротив, не имеет отношения, так как в Perl в основном используются обратные кавычки для вызова shell-функций. Как отметил paulus, лучше эти скритпы прямо писать на bash.
13.10.2008, 23:26
Ответить
NO USERPIC

codeart

мне кажется в случае создания "Живого бэкапа" для проверки корректности загруженных данных лучше использовать такие системы как, например, Selenium, а не полагаться на загрузку только первой страницы.
14.10.2008, 17:49
Ответить
NO USERPIC

denlem

Идея интересная.. Но позволю заметить для каких сайтов это возможно делать - для небольших, которые немного обновляются, не сильно грузят базу, имеют небольшой контент, имеют не сложные настройки. Для больших сайтов со сложными настройкаи это не применимо, потому что во-первых: большой контент бекапа занимает большую часть на серваке места, а соответственно, его лучше хранить в архиве, далее - много банеров, информеров, реклам плагинов, в том числе и платных, а также счетчиков - как правило завязаны на одном домене и при переносе создадут дискомфорт как интерфейсу, так и удаленным сервакам к которым они конектятс при загрузке сайта.......
а в целом идей неплохая - это небольшой плюсик в поднятии престижа кмске или дизайн студии
23.10.2008, 19:03
Ответить
NO USERPIC

rgbeast

Совершенно правильное замечание. Для больших сайтов не подойдет. В случае больших сайтов имеет смысл думать про систему резервирования, которая использует репликацию быза данных. Статья адресована сайтам среднего размера (скажем, база данных не превосходит гигабайт), которых в интернете 99%, и для которых, к сожалению, часто совсем отсутствует backup. Если у сайта сложные настройки, то можно дополнить скрипт так, чтобы он необходимое перенастраивал (и некоторые модули отключал) на backup-сервере. Отмечу, что модули систем широкого пользования (Яндекс-директ, google adsense, счетчики и др.) ведут себя корректно при переносе.
23.10.2008, 19:18
Ответить
Добавить комментарий
Отображение комментариев: Древовидное | Плоское
© 2008—2024 webew.ru, связаться: x собака webew.ru
Сайт использует Flede и соответствует стандартам WAI-WCAG 1.0 на уровне A.
Rambler's Top100

Реклама: