Harada's Diary

rsyncとlsyncdでリアルタイムにディレクトリを同期する

差分を算出してファイルやディレクトリを同期してくれる rsync と
ローカルファイルへの変更を監視してくれる lsyncd を組み合わせることで
リアルタイムにディレクトリを同期することができます。

lsyncd と rsync を連動する方法は二つあります。

  • SSH を通して rsync 同士が通信する方法
  • バックアップ先で rsync デーモンを動かす方法

rsync をデーモンモードで動作させることで、
rsync プロトコル(rsync://)による同期が可能になり、
SSH を利用する場合より暗号化によるオーバーヘッドがなく高速で同期することができます。


前提環境

ホストOS

IPアドレス

同期対象ディレクトリ

マスター

CentOS 6.8

10.0.0.6

/var/www/html/

スレーブ

CentOS 6.8

10.0.0.7

/var/www/html/

同期対象のディレクトリは Apache のデフォルトのドキュメントルートを指定するので、
あらかじめ Apache のインストールも必要になります。


lsyncd + rsync のインストール

マスター側には lsyncd / rsync、スレーブ側には rsync をインストールします。

\マスター側 # yum -y install lsyncd # yum -y install rsync \スレーブ側 # yum -y install xinetd # yum -y install rsync 

これでインストールは完了です。


lsyncd の設定 [マスター側]

lsyncd.conf を設定します。
/etc/lsyncd.conf に下記を追記します。

# vi /etc/lsyncd.conf settings{ logfile = "/var/log/lsyncd.log", statusFile = "/tmp/lsyncd.stat", statusInterval = 1, } sync{ default.rsync, source="/var/www/html/", target="10.0.0.7::sync", rsync = { _extra = { "-a" }, } } 

ざっくり解説すると、settings でログやステータスの出力先を設定し、
sync セクションで同期元ディレクトリ(source)と同期先(target)を指定します。

同期先の target にある ::syncsyncモジュール名 で、
このあと設定する スレーブ側 rsyncd.conf のモジュール名 と一致していれば OK です。


lsyncd の起動 [マスター側]

自動起動の設定をして…

# chkconfig lsyncd on 

lsyncd を起動します。(この時点ではスレーブ側の設定がまだなら、起動に失敗する場合があります)

# /etc/rc.d/init.d/lsyncd start 

rsync の設定 [スレーブ側]

スレーブ側の設定は xinetdrsyncd の 2 つです。
まず xinetd の設定ファイルを編集します。

# vi /etc/xinetd.d/rsync service rsync { disable = no # yes から no に変更 flags = IPv6 socket_type = stream wait = no user = root server = /usr/bin/rsync server_args = --daemon log_on_failure += USERID } 

user は root 以外にしても構いませんが、ここでは簡単のため root のままにしています。

xinetd を自動起動にして起動します。

# chkconfig xinetd on # service xinetd start 

rsyncd.conf の設定 [スレーブ側]

スレーブ側の rsyncd.conf を設定します。
(xinetd に叩かれたときの rsync デーモンの挙動になります)

# vi /etc/rsyncd.conf # マスター側 lsyncd.conf 内の target と同じモジュール名にする [sync] # コピー先対象ディレクトリ path = /var/www/html/ hosts allow = localhost 10.0.0.6 list = true uid = root gid = root read only = false port = 873 

ポイントは [sync] の部分で、これがリアルタイム同期の モジュール になります。
マスター側 target="10.0.0.7::sync"sync がここです。

ここで同期先ディレクトリ・許可するホスト・ポート番号などを設定します。


マスター側の lsyncd を起動する

順番が前後している場合は、もう一度 lsyncd を起動しておきます。
(本来はスレーブ側設定 → マスター側設定の順番が望ましいです)

# /etc/rc.d/init.d/lsyncd start 

ここまでできたら大筋完成です。

  • スレーブ側で xinetd が待機して rsync --daemon を起動できる状態にする
  • マスター側 lsyncd が差分検知 → rsync で送信
  • スレーブ側の xinetd がそれを受けて rsyncd に渡す

という流れになります。

ログも確認してみましょう。

# less /var/log/lsyncd.log Mon May 1 00:31:17 2017 Normal: recursive startup rsync: /var/www/html/ -> 10.0.0.7::sync/ Mon May 1 00:31:22 2017 Normal: Startup of "/var/www/html/" finished. Mon May 1 00:32:12 2017 Normal: Calling rsync with filter-list of new/modified files/dirs 

ログにきちんと出ていれば OK です。
試しにマスター側で test ファイルを生成すると、スレーブ側にも自動で同期されるはずです。


※余談
スレーブ側のファイルを手動でいじるとどうなるか? という疑問もあると思いますが、
かなりおかしな状態になる可能性が高いので、基本は「スレーブは触らない」 運用がおすすめです。
(いろいろ工夫したい場合は、競合時のポリシーなどを含めて別途調査したほうがよいです)