Серверы · 5 min read · Oct 08, 2025

Идеальный сбалансированный и высокодоступный веб-кластер с 2 серверами, работающими под Xen на Ubuntu 8.04 Hardy Heron - Страница 8

14. Зеркалирование веб- и почтовых файлов с помощью rsync (web1, web2)

Это сложная часть. В зависимости от типа веб-сайта(ов), которые вы разместите в кластере, техника, используемая для зеркалирования веб-файлов, может отличаться.

Мы будем считать web1.example.com основным, web2.example.com будет синхронизироваться с web1.example.com

Это может создать проблемы в некоторых случаях. Если у вас есть веб-сайт, на который пользователи могут загружать файлы, вы не хотите, чтобы они загружались на web2.example.com, потому что два сервера не будут синхронизированы.

В моем случае я перенаправляю все страницы, на которых пользователи могут загружать данные, на HTTP-порт 81, который перенаправляется только на один сервер, web1.example.com. Если основной сервер выходит из строя, весь трафик порта 81 перенаправляется на резервный сервер, web2.example.com, и зеркалирование временно останавливается.

Перенаправление можно сделать в apache vhost.conf :

[...]
Redirect /admin http://www.example.com:81/webmail
[...]

Если у вас много загрузок файлов пользователями, вы можете рассмотреть возможность использования балансировки нагрузки NFS :

https://www.howtoforge.com/high_availability_nfs_drbd_heartbeat

14.1 Установите rsync

apt-get install rsync

14.2 Создайте ключи на web2.example.com

Теперь мы создаем пару закрытого/открытого ключа на web2.example.com:

mkdir /root/rsync
ssh-keygen -t dsa -b 1024 -f /root/rsync/mirror-rsync-key

Вы увидите что-то вроде этого:

Generating public/private dsa key pair.
Enter passphrase (empty for no passphrase): [нажмите enter здесь]
Enter same passphrase again: [нажмите enter здесь]
Your identification has been saved in /root/rsync/mirror-rsync-key.
Your public key has been saved in /root/rsync/mirror-rsync-key.pub.
The key fingerprint is:
68:95:35:44:91:f1:45:a4:af:3f:69:2a:ea:c5:4e:d7 root@web2

Важно, чтобы вы не вводили пароль, иначе зеркалирование не будет работать без человеческого взаимодействия, просто нажмите enter!

Далее, мы копируем наш открытый ключ на web1.example.com:

scp /root/rsync/mirror-rsync-key.pub [email protected]:/home/vmail/

Открытый ключ mirror-rsync-key.pub теперь должен быть доступен в /home/vmail на web1.example.com.

14.3 Настройте web1.example.com

web1.example.com

Теперь войдите через SSH как vmail (не root!) и сделайте следующее:

login vmail

mkdir ~/.ssh
chmod 700 ~/.ssh
mv ~/mirror-rsync-key.pub ~/.ssh/
cd ~/.ssh
touch authorized_keys
chmod 600 authorized_keys
cat mirror-rsync-key.pub >> authorized_keys

Таким образом, мы добавили содержимое mirror-rsync-key.pub в файл /home/vmail/.ssh/authorized_keys. /home/vmail/.ssh/authorized_keys должен выглядеть примерно так:

(Все еще как webmaster! на web1.example.com)

vi ~/.ssh/authorized_keys

ssh-dss AAAAB3NzaC1kc3MAAA[...]lSUom root@web2

Теперь мы хотим разрешить подключения только от web2.example.com, и подключающийся пользователь должен иметь возможность использовать только rsync, поэтому мы добавляем

command="/home/vmail/rsync/checkrsync",from="192.168.0.105",no-port-forwarding,no-X11-forwarding,no-pty

сразу в начале /home/vmail/.ssh/authorized_keys:

command="/home/vmail/rsync/checkrsync",from="192.168.0.105",no-port-forwarding,no-X11-forwarding,no-pty ssh-dss AAAAB3NzaC1kc3MAAA[...]lSUom root@
web2

Теперь мы создаем скрипт /home/vmail/rsync/checkrsync, который отклоняет все команды, кроме rsync на web1.example.com.

(Мы все еще делаем это как vmail!)

mkdir ~/rsync
vi ~/rsync/checkrsync

#!/bin/sh



case "$SSH_ORIGINAL_COMMAND" in
        *\&*)
                echo "Rejected"
                ;;
        *\(*)
                echo "Rejected"
                ;;
        *\{*)
                echo "Rejected"
                ;;
        *\;*)
                echo "Rejected"
                ;;
        *\<*)
                echo "Rejected"
                ;;
        *\`*)
                echo "Rejected"
                ;;
        rsync\ --server*)
                $SSH_ORIGINAL_COMMAND
                ;;
        *)
                echo "Rejected"
                ;;
esac

chmod 700 ~/rsync/checkrsync

14.4 Протестируйте автоматизированный rsync

web2.example.com

Сначала мы должны сказать rsync, какие файлы мы не хотим синхронизировать (такие как график модуля!)

vi /root/exclude_www.txt

и сделать его таким:

 /example/web/monit/
 /example/web/monitoring/
 /example/ssl/
 /yoursite/ssl/ 

а теперь для почты:

vi /root/exclude_mail.txt

/rsync/
/.ssh/
#if you use my monitoring script, see next page
server1_was_down/
.bash_history/
.bash_logout/
.bashrc/
.mysql_history/
.profile/
.viminfo/

Теперь мы должны протестировать на web2.example.com, можем ли мы зеркалировать web1.example.com без запроса пароля vmail. Мы делаем это:

(Мы делаем это как root!)

web2.example.com

rsync -avz –delete –ignore-errors –exclude-from ‘/root/exclude_www.txt’ -e “ssh -i /root/rsync/mirror-rsync-key” [email protected]:/var/www/ /var/www/

за которым следует:

rsync -avz –delete –ignore-errors –exclude-from ‘/root/exclude_mail.txt’ -e “ssh -i /root/rsync/mirror-rsync-key” [email protected]:/home/vmail/ /home/vmail/

Теперь вы должны увидеть, что зеркалирование происходит без запроса пароля:

receiving file list ... done
sent 71 bytes  received 643 bytes  476.00 bytes/sec
total size is 64657  speedup is 90.56

14.5 Создайте задачу cron

Сначала мы создадим скрипт, который убедится, что если по какой-то причине web1.example.com вышел из строя, rsync будет остановлен, и root должен будет вручную перезапустить процесс.

Причина, по которой мы должны это сделать, заключается в том, что web2.example.com возьмет на себя web1.example.com для почты, если он выйдет из строя. Новая почта будет получена на web2.example.com в этот период, так что, скажем, web1.example.com вернется в онлайн через час, вся новая почта за этот период времени будет удалена на web2.example.com из-за команды rsync –delete. Мы увидим ниже, как синхронизировать оба сервера, если это произойдет.

Пока давайте напишем этот скрипт.

На web2.example.com

vi /root/rsync_web1

#!/bin/bash
# Скрипт для rsync веб-данных и почты между 2 сбалансированными серверами
# Copyright (c) 2008 blogama.org
# Этот скрипт лицензирован под GNU GPL версии 2.0 или выше
# ---------------------------------------------------------------------
### Этот скрипт имеет 2 цели ###
### 1) Проверить соединение на порту 25 с основным сервером, а затем rsync почту ###
### 2) Проверить соединение на порту 80 с основным сервером, а затем rsync www данные ###
### Для изменения ###
MASTERSERVERIP="192.168.0.104"
WEBPORT="80"
SMTPPORT="25"
SSHPORT="22"
EMAIL="[email protected]"
WWWRSYNCUSER="vmail"
WWWDIR="/var/www/"
MAILRSYNCUSER="vmail"
MAILDIR="/home/vmail/"

###### Не вносите изменения ниже ######
### Бинарные файлы ###
MAIL=$(which mail)
TELNET=$(which telnet)
RSYNC=$(which rsync)
SSH=$(which ssh)
### Чтобы восстановить оригинал, когда проблема будет исправлена ###
if [ $1 ]; then
  if [ $1=="fix" ]; then
    if [ -f smtp_down.txt ]; then
      rm /root/smtp_down.txt
    fi
    if [ -f www_down.txt ]; then
      rm /root/www_down.txt
    fi
  fi
fi
####################SMTP####################
### Если уже уведомлены о проблеме SMTP, выход ###
cd /root
if [ -f smtp_down.txt ]; then
  exit 1;
fi
### Проверить, отвечает ли сервер 1 на SMTP. Если да, rsync почту ###
### Если сервер 1 был отключен, нельзя rsync --delete сервер 2 с 1 ###
### Должен синхронизировать сервер1 с 2 (без удаления) и запустить /root/sync fix ###
(
echo "quit"
) | $TELNET $MASTERSERVERIP $SMTPPORT | grep Connected > /dev/null 2>&1
if [ "$?" -ne "1" ]; then
  $RSYNC -avz --delete --ignore-errors --exclude-from '/root/exclude_mail.txt' -e "ssh -p $SSHPORT -i /root/rsync/mirror-rsync-key" $MAILRSYNCUSER@$MASTERSERVERIP:$MAILDIR $MAILDIR
else
  echo "Сервер 1 отключен. Синхронизация почты больше не работает" > /root/smtp_down.txt
  $MAIL -s "Сервер 1 отключен порт 25" $EMAIL < /root/smtp_down.txt
fi
####################HTTP####################
### Если уже уведомлены о проблеме HTTP, выход ###
cd /root
if [ -f http_down.txt ]; then
  exit 1;
fi
### Проверить, отвечает ли сервер 1 на HTTP. Если да, rsync www данные ###
(
echo "quit"
) | $TELNET $MASTERSERVERIP $WEBPORT | grep Connected > /dev/null 2>&1
if [ "$?" -ne "1" ]; then
  $RSYNC -avz --delete --ignore-errors --exclude-from '/root/exclude_www.txt' -e "ssh -p $SSHPORT -i /root/rsync/mirror-rsync-key" $WWWRSYNCUSER@$MASTERSERVERIP:$WWWDIR $WWWDIR
else
  echo "Сервер 1 отключен. Синхронизация WWW больше не работает" > /root/http_down.txt
  $MAIL -s "Сервер 1 отключен порт 80" $EMAIL < /root/http_down.txt
fi

И сделайте этот файл исполняемым:

chmod +x /root/rsync_web1

Конечно, вы можете положить что угодно в эти файлы ;) Если вы не поставите слэш, он будет игнорировать ключевое слово рекурсивно (например: *.gz), если вы поставите слэш, это будет для точного местоположения (например: /example/ssl/).

Теперь мы добавим скрипт в наш crontab, сделав следующее:

crontab -e

и добавим эту строку:

[...]
*/5 * * * * /root/rsync_web1  >/dev/null 2>&1
[...]

Это будет запускать его каждые 5 минут, конечно, вы можете изменить это по своему усмотрению.

14.6 Что если web1.example.com был отключен

В общем, если web1.example.com отключен, вам нужно:

  1. rsync WEB1 TO WEB2 без команды –delete :

web1.example.com

rsync -avz [email protected]:/var/www/ /var/www/
rsync -avz [email protected]:/home/vmail/ /home/vmail/

Share: X/Twitter LinkedIn

Get new posts in your inbox

No spam. Unsubscribe anytime.