В статье рассмотрим, как создать систему резервирования и репликации баз данных для веб-сайтов, которая обеспечит их доступность даже при сбоях хостинга.
Такое решение будет полезно тем, кто сталкивается с нестабильными хостингами, хочет избежать потери данных и минимизировать время простоя.
Вы узнаете, как настроить автоматическую синхронизацию данных между основным и резервным серверами, используя Cloudflare и PHP. И сможете воспользоваться готовым скриптом, который мы разработали для решения этой задачи.
Логичное решение — использовать балансировщики нагрузки (собственные или готовые). В данном случае мы решили обратиться к Cloudflare.
Балансировку настроили, однако даже с настроенным автоматическим переключением оставалась задача синхронизации данных: код сайтов остается прежним, но контент постоянно обновляется. Чтобы пользователи всегда видели актуальную информацию, нужно поддерживать идентичность данных на хостингах.
Поэтому мы сосредоточились на репликации баз данных между мастер-сервером и резервным хостингом, чтобы изменения автоматически отражались на обоих. Готовые продукты на рынке есть, но мы искали более бюджетный вариант, подходящий для наших целей, и пришли к решению собственной разработки.
Преимущества:
Добавление домена.
Load Balancing.
Добавление IP.
Создание нового балансировщика.
Указание домена.
Завершение настройки балансировщика.
Обязательно протестируйте переключение на резервный хостинг и не забудьте после этого вернуть все обратно.
// Создаем бэкап базы данных$backupFile = '/path/to/backup.sql';exec("mysqldump --user={$dbUser} --password={$dbPass} --host={$dbHost} {$dbName} > {$backupFile}");// Архивируем$zip = new ZipArchive();$zipFile = '/path/to/backup.zip';if ($zip->open($zipFile, ZipArchive::CREATE) === TRUE) { $zip->addFile($backupFile, 'backup.sql'); $zip->close();}// Отправляем архив на Slave$curl = curl_init();curl_setopt_array($curl, [ CURLOPT_URL => "
Этот код создает резервную копию базы данных и отправляет её на сервер:
class RestoreController { private string $backupDir = '/path/to/backup'; private string $backupFile = 'backup.zip'; private string $sqlFile = 'backup.sql'; public function receiveBackup($file) { if ($file['error'] === UPLOAD_ERR_OK) { move_uploaded_file($file['tmp_name'], "{$this->backupDir}/{$this->backupFile}"); return ['status' => 'success', 'message' => 'Файл успешно загружен']; } return ['status' => 'error', 'message' => 'Ошибка загрузки файла']; } public function restoreDatabase() { $zip = new ZipArchive(); if ($zip->open("{$this->backupDir}/{$this->backupFile}") === TRUE) { $zip->extractTo($this->backupDir); $zip->close(); } else { return ['status' => 'error', 'message' => 'Не удалось распаковать бэкап']; } $pdo = new PDO("mysql:host={$dbHost};dbname={$dbName}", $dbUser, $dbPass); $sql = file_get_contents("{$this->backupDir}/{$this->sqlFile}"); $pdo->exec($sql); return ['status' => 'success', 'message' => 'База данных успешно восстановлена']; }}// Получаем запрос$restoreController = new RestoreController();if ($_FILES) { $response = $restoreController->receiveBackup($_FILES['file']); echo json_encode($response);} elseif ($_POST['action'] === 'runrestore') { $response = $restoreController->restoreDatabase(); echo json_encode($response);}
Этот код реализует контроллер для восстановления базы данных:
1. Получение данных и выполнение действий
После успешной загрузки архива запускается процесс восстановления базы данных через RestoreController, который включает следующие шаги:
Запросы на Slave могут быть двух типов:
После успешной загрузки архива запускается процесс восстановления базы данных через RestoreController, который включает следующие шаги:
Запросы на Slave могут быть двух типов:
Как это работает в связке с Master.
Таким образом, система обеспечивает автоматический процесс резервного копирования, передачи и восстановления данных между серверами Master и Slave, поддерживая их синхронизацию.
1. Подготовка папок на серверах:
На хостинге 1 (Master) создаем в корне сайта папку backup и помещаем в нее все файлы из папки Master.
На хостинге 2 (Slave) создаем аналогичную папку backup и помещаем в нее все файлы из папки Slave.
2. Настройка доступа на Master:
На хостинге 1 (Master) идем в папку backup и открываем файл Config.php. Здесь необходимо указать данные для подключения к серверу Slave.Также здесь можно задать папку, куда будут сохраняться копии БД. В нашем случае /upload.
3. Если вы используете WordPress, скрипт автоматически извлечет данные из файла wp-config.php, так что вам не нужно будет беспокоиться о подключении.
Если у вас не WordPress, просто укажите свои данные для подключения к базе данных в файле backup/Config.php на Master и в backup/src/Config.php на Slave.
Код.
4. Настройка Cron:
Теперь нужно настроить задачи в Cron для Master, которые будут запускаться раз в час для каждого сайта. Рекомендую не ставить все задачи на одно и то же время, лучше задать интервал в 15 минут между ними. Так вы избежите нагрузки на сервер.
Используйте команду:
Команда.
Полный путь можно посмотреть на вашем хостинге. Это обеспечит автоматическое создание бэкапов и их передачу на Slave.
Такое решение будет полезно тем, кто сталкивается с нестабильными хостингами, хочет избежать потери данных и минимизировать время простоя.
Вы узнаете, как настроить автоматическую синхронизацию данных между основным и резервным серверами, используя Cloudflare и PHP. И сможете воспользоваться готовым скриптом, который мы разработали для решения этой задачи.
Проблема
Клиент обратился к нам с задачей, касающейся шести ресурсов на WordPress. Это были новостные издания, посвященные спортивным событиям. Сообщения об их недоступности приходили регулярно, сайты не работали и теряли пользователей. Необходимость изменений стала очевидной: клиент хотел обеспечить доступность ресурсов даже при падении основного хостинга.Логичное решение — использовать балансировщики нагрузки (собственные или готовые). В данном случае мы решили обратиться к Cloudflare.
Балансировку настроили, однако даже с настроенным автоматическим переключением оставалась задача синхронизации данных: код сайтов остается прежним, но контент постоянно обновляется. Чтобы пользователи всегда видели актуальную информацию, нужно поддерживать идентичность данных на хостингах.
Поэтому мы сосредоточились на репликации баз данных между мастер-сервером и резервным хостингом, чтобы изменения автоматически отражались на обоих. Готовые продукты на рынке есть, но мы искали более бюджетный вариант, подходящий для наших целей, и пришли к решению собственной разработки.
Репликация данных через бэкапы
Для решения задачи разработали скрипт, который действует следующим образом:- На Хостинге 1 (Master) раз в час создается бэкап базы данных.
- Этот бэкап отправляется на Хостинг 2 (Slave), где база данных восстанавливается.
- Каждый час происходит сравнение данных, и если на Master было изменение, то на Slave база обновляется.
Автоматизация процесса:
Скрипт запускается автоматически через Cron для каждого сайта. Это гарантирует актуальность данных и синхронизацию между хостингами, что особенно важно при переключении на резервный сервер.
Преимущества:
- Высокая доступность: сайты работают даже при сбоях хостинга.
- Автоматическая синхронизация: избегаете потерь данных и рассинхронизации.
- Минимальное время простоя: пользователи не заметят проблем с доступом к сайтам.
Дублирование сайтов
Дублирование сайтов осуществляется следующим образом:- На новом хостинге добавляете новый домен (он нужен, чтобы запустить сайты) и создаете поддомены для каждого сайта. В нашем случае 6 поддоменов, так как у нас 6 сайтов.
- Каждому сайту с поддоменом присваиваете оригинальный домен. Обратите внимание, что SSL-сертификаты не создаются через хостинг, а будут получены через Cloudflare.
Настройка Cloudflare
Создайте аккаунт Cloudflare для каждого из своих сайтов. Настройка будет одинаковой для всех. Чтобы не утонуть в подробностях, покажу только основные шаги, из которых будет понятно, как это сделать.- В разделе Websites добавьте ваш домен, нажав на кнопку Add a domain.
Добавление домена.
- Перейдите в меню DNS и пропишите NS-серверы, которые выдал Cloudflare, у регистратора домена.
- Добавьте по две A-записи для каждого IP от ваших двух хостингов (для домена и www). Убедитесь, что Proxy status установлен на Proxied.
Настройка балансировщика нагрузки
- Перейдите в раздел Traffic — Load Balancing.
Load Balancing.
- Нажмите Manage Monitors — Create и добавьте IP для первого хостинга.
Добавление IP.
- Создайте новый балансировщик, нажав Create Load Balancer.
Создание нового балансировщика.
- Укажите свой домен, выберите оба пула и добавьте их в таблицу.
Указание домена.
Завершение настройки балансировщика.
Обязательно протестируйте переключение на резервный хостинг и не забудьте после этого вернуть все обратно.
Создание системы бэкапов Master-Slave на PHP
Теперь перейдем к важной части — как задублировать данные с помощью системы Master-Slave.Почему стоит использовать систему Master-Slave?
- Автоматизация: не придется вручную переживать за бэкапы — все происходит по расписанию.
- Отказоустойчивость: если ваш Master-сервер решит взять выходной, Slave всегда наготове.
- Масштабируемость: легко добавлять новые сайты или базы данных в систему.
- Минимизация риска потерь: благодаря регулярной синхронизации вы защищены от потери данных.
Общий функционал системы Master-Slave
На стороне Master (описанной ранее) создается резервная копия базы данных, она архивируется и передается на Slave-серверы для последующего восстановления. На стороне Slave реализован прием архивов с бэкапами и их разархивирование, после чего данные из бэкапа восстанавливаются в базу данных.Шаг 1: Настройка Master-сервера
На Master-сервере:- Создание бэкапа базы данных: используйте mysqldump, чтобы вытащить данные в файл.
- Архивирование: ZIP-архив, чтобы сохранить все в целости.
- Передача бэкапа на Slave: отправьте архив с помощью cURL.
// Создаем бэкап базы данных$backupFile = '/path/to/backup.sql';exec("mysqldump --user={$dbUser} --password={$dbPass} --host={$dbHost} {$dbName} > {$backupFile}");// Архивируем$zip = new ZipArchive();$zipFile = '/path/to/backup.zip';if ($zip->open($zipFile, ZipArchive::CREATE) === TRUE) { $zip->addFile($backupFile, 'backup.sql'); $zip->close();}// Отправляем архив на Slave$curl = curl_init();curl_setopt_array($curl, [ CURLOPT_URL => "
Для просмотра ссылки необходимо нажать
Вход или Регистрация
", CURLOPT_POST => true, CURLOPT_POSTFIELDS => [ 'file' => new CURLFile($zipFile) ], CURLOPT_RETURNTRANSFER => true]);$response = curl_exec($curl);curl_close($curl);echo "Ответ от Slave: $response";Этот код создает резервную копию базы данных и отправляет её на сервер:
- Создание бэкапа — с помощью команды mysqldump выполняется экспорт базы данных в SQL-файл.
- Архивирование — создается ZIP-архив, в который добавляется SQL-файл.
- Отправка на Slave-сервер — архив отправляется через cURL на удалённый сервер для дальнейшего хранения.
Шаг 2: Настройка Slave-сервера
На Slave-сервере:- Прием архива от Master: сохраняем полученный бэкап.
- Распаковка архива: открываем его, чтобы достать SQL-файл.
- Восстановление базы данных: исполняем SQL-файл.
class RestoreController { private string $backupDir = '/path/to/backup'; private string $backupFile = 'backup.zip'; private string $sqlFile = 'backup.sql'; public function receiveBackup($file) { if ($file['error'] === UPLOAD_ERR_OK) { move_uploaded_file($file['tmp_name'], "{$this->backupDir}/{$this->backupFile}"); return ['status' => 'success', 'message' => 'Файл успешно загружен']; } return ['status' => 'error', 'message' => 'Ошибка загрузки файла']; } public function restoreDatabase() { $zip = new ZipArchive(); if ($zip->open("{$this->backupDir}/{$this->backupFile}") === TRUE) { $zip->extractTo($this->backupDir); $zip->close(); } else { return ['status' => 'error', 'message' => 'Не удалось распаковать бэкап']; } $pdo = new PDO("mysql:host={$dbHost};dbname={$dbName}", $dbUser, $dbPass); $sql = file_get_contents("{$this->backupDir}/{$this->sqlFile}"); $pdo->exec($sql); return ['status' => 'success', 'message' => 'База данных успешно восстановлена']; }}// Получаем запрос$restoreController = new RestoreController();if ($_FILES) { $response = $restoreController->receiveBackup($_FILES['file']); echo json_encode($response);} elseif ($_POST['action'] === 'runrestore') { $response = $restoreController->restoreDatabase(); echo json_encode($response);}
Этот код реализует контроллер для восстановления базы данных:
- receiveBackup — загружает файл резервной копии на сервер.
- restoreDatabase — распаковывает бэкап, извлекает SQL-файл и восстанавливает базу данных через PDO.
- Обработка запросов — загрузка файла или запуск восстановления базы данных через POST-запрос.
Конфигурация системы
Основные компоненты на стороне Slave:- SlaveController: главный контроллер, который управляет получением и восстановлением данных.
- ReceiveFileController: контроллер для обработки загрузки файлов от Master.
- RestoreController: контроллер для восстановления базы данных из архива.
- ConfigController: контроллер для получения конфигурации сервера и базы данных.
- ReceiveFileRepository: репозиторий для сохранения полученных файлов и проверки их целостности.
1. Получение данных и выполнение действий
- Главный контроллер SlaveController обрабатывает входящие запросы.
- Если в запросе передан параметр action=runrestore, запускается процесс восстановления базы данных.
- Если в запросе переданы файлы (например, архив backup.zip), запускается процесс получения файла через ReceiveFileController.
- Когда Master отправляет архив бэкапа на Slave, файл принимается с помощью ReceiveFileController и сохраняется в директорию, указанную в конфигурации ($DUMP_DIR).
- Если файл загружен успешно, создается контрольная сумма файла для дальнейшего сравнения с контрольной суммой на стороне Master, чтобы убедиться, что файл передан корректно.
После успешной загрузки архива запускается процесс восстановления базы данных через RestoreController, который включает следующие шаги:
- Распаковка архива с бэкапом.
- Восстановление базы данных из файла backup.sql, который был извлечен из архива.
- Каждая строка SQL-файла выполняется по очереди, и данные восстанавливаются в базу данных.
- Конфигурация для Slave-сервера задается в классе ConfigController, который определяет параметры для подключения к базе данных и пути для хранения дампов.
- В зависимости от типа сервера (обычный или WordPress), конфигурация может быть взята либо из предустановленных параметров, либо из файла wp-config.php (для WordPress).
Запросы на Slave могут быть двух типов:
- Прием файла архива с бэкапом от Master (ReceiveFileController).
- Восстановление базы данных на основе полученного архива (RestoreController).
- Главный контроллер SlaveController обрабатывает входящие запросы.
- Если в запросе передан параметр action=runrestore, запускается процесс восстановления базы данных.
- Если в запросе переданы файлы (например, архив backup.zip), запускается процесс получения файла через ReceiveFileController.
- Когда Master отправляет архив бэкапа на Slave, файл принимается с помощью ReceiveFileController и сохраняется в директорию, указанную в конфигурации ($DUMP_DIR).
- Если файл загружен успешно, создается контрольная сумма файла для дальнейшего сравнения с контрольной суммой на стороне Master, чтобы убедиться, что файл передан корректно.
После успешной загрузки архива запускается процесс восстановления базы данных через RestoreController, который включает следующие шаги:
- Распаковка архива с бэкапом.
- Восстановление базы данных из файла backup.sql, который был извлечен из архива.
- Каждая строка SQL-файла выполняется по очереди, и данные восстанавливаются в базу данных.
- Конфигурация для Slave-сервера задается в классе ConfigController, который определяет параметры для подключения к базе данных и пути для хранения дампов.
- В зависимости от типа сервера (обычный или WordPress), конфигурация может быть взята либо из предустановленных параметров, либо из файла wp-config.php (для WordPress).
Запросы на Slave могут быть двух типов:
- Прием файла архива с бэкапом от Master (ReceiveFileController).
- Восстановление базы данных на основе полученного архива (RestoreController).
Как это работает в связке с Master
Как это работает в связке с Master.
Таким образом, система обеспечивает автоматический процесс резервного копирования, передачи и восстановления данных между серверами Master и Slave, поддерживая их синхронизацию.
Практическая установка
Теперь перейдем к самой настройке. В архиве
Для просмотра ссылки необходимо нажать
Вход или Регистрация
вы можете найти готовый скрипт, который мы разработали для решения этой задачи. Там находятся две папки: Master и Slave.1. Подготовка папок на серверах:
На хостинге 1 (Master) создаем в корне сайта папку backup и помещаем в нее все файлы из папки Master.
На хостинге 2 (Slave) создаем аналогичную папку backup и помещаем в нее все файлы из папки Slave.
2. Настройка доступа на Master:
На хостинге 1 (Master) идем в папку backup и открываем файл Config.php. Здесь необходимо указать данные для подключения к серверу Slave.Также здесь можно задать папку, куда будут сохраняться копии БД. В нашем случае /upload.
3. Если вы используете WordPress, скрипт автоматически извлечет данные из файла wp-config.php, так что вам не нужно будет беспокоиться о подключении.
Если у вас не WordPress, просто укажите свои данные для подключения к базе данных в файле backup/Config.php на Master и в backup/src/Config.php на Slave.
Код.
4. Настройка Cron:
Теперь нужно настроить задачи в Cron для Master, которые будут запускаться раз в час для каждого сайта. Рекомендую не ставить все задачи на одно и то же время, лучше задать интервал в 15 минут между ними. Так вы избежите нагрузки на сервер.
Используйте команду:
Команда.
Полный путь можно посмотреть на вашем хостинге. Это обеспечит автоматическое создание бэкапов и их передачу на Slave.
Проверка работоспособности
После всех настроек стоит убедиться, что система работает корректно:- Проверьте, создаются ли бэкапы на Master.
- Убедитесь, что данные успешно передаются и восстанавливаются на Slave.
- Периодически тестируйте процесс восстановления, чтобы быть уверенным, что все работает как часы.
Поддержка системы
Поддерживать систему Master-Slave достаточно просто, если соблюдать несколько правил:- Регулярные проверки: следите за состоянием обоих серверов. Проверяйте, чтобы бэкапы действительно создавались и восстанавливались.
- Мониторинг нагрузки: убедитесь, что Slave-сервер не перегружен, особенно если он начинает принимать много запросов.
- Тестирование восстановления: периодически проводите тесты на восстановление, чтобы убедиться, что бэкапы работают.
Для просмотра ссылки необходимо нажать
Вход или Регистрация