こんにちは、 株式会社 日立製作所 OSSソリューションセンタ の 神山直也(hi-naoya) です。
日立グループ OSS Advent Calendar 2018 の11日目、書かせて頂きたく。
私は社内システムの設計、構築、運用、etc …ゆりかごから墓場まで面倒を見ています。
今回は運用には欠かせないバックアップについて、「rsyncコマンド(とcron)だけで、差分・完全バックアップを取得する」方法をご紹介します。
はじめに
前提条件:
- 本番環境1、2台の小規模環境
- ミッションクリティカルではない
- CentOS 7.x で動作するシステム
- バックアップ対象は数百G〜数T程度のファイル
- 1週間に1回完全バックアップ、毎日差分バックアップしたい
商用の製品から、バックアップを目的としたOSSなど、バックアップを行うソフトウェアはたくさんあります。
今回は rsync を利用していきます。(今回は、2018/12/11 時点の CentOS 7.5 でインストール可能な、rsync version 3.1.2 protocol version 31 を利用しています。)
rsync
rsync は古くから存在する遠隔地間のファイル・ディレクトリを同期するツールです。
専用プロトコルにより高速な同期が可能であり、SSH経由で同期できるなど、同期に関してはかなりツボを押さえたツールとなっています。
参考:
同期元・先のディレクトリを指定して、ファイルの数や内容が一致するようにコピーする、といった用法が一般的ですが、ハードリンクを利用した差分バックアップ機能も持っており、それを利用すれば高度な完全バックアップ・差分バックアップの運用が可能になります。
完全バックアップ
rsync -a --delete src/ dest/
-a オプションは、「アーカイブ・モード」でコピーするオプションで、ディレクトリやファイルを、そのメタ情報込みで同期するオプションです。
--delete は、削除されたファイルがあった場合に、同期先からファイルを削除するオプションです。
注意:
rsync はパスを指定する際に、/path/to/ と指定するか、/path/to と指定するかで動作が変わります。前者は、/path/to ディレクトリの中身全てを対象としますが、後者は /path/to ディレクトリを対象とします。この指定を間違えると、差分バックアップを採る際に、ディレクトリ構造が一致せず、問題となってしまいます(実際にハマりました)。
差分バックアップ
rsync -a --delete --link-dest=/path/link_dest/ /path/src/ /path/dest/
ほとんど、完全バックアップと同じですが、--link-dest
オプションが増えています。
このオプションをつけると、変更のないファイルは、/path/link_dest/ と /path/dest/ で共有されます(ハードリンクによりファイルがコピーされる)。
ディスクの消費は、/path/link_dest にバックアップを採った時点〜コマンド実行時点の間で変更のあったファイルのみとなります。
一般的に差分バックアップを復元する際は、復元操作が必要なことがありますが、
この方法で差分バックアップを採った場合は、ファイルシステム上 /path/src/ も /path/dest/ も完全なディレクトリ構造を保持しているので、差分バックアップを参照する際に特別な操作が不要であり、単純なファイル操作で参照できます。
バックアップの運用
cron にて定期実行することで、自動的にバックアップを取得しています。
- 1週間に1回
- 完全バックアップ
- 毎日(完全バックアップ以外の日)
- 完全バックアップからの差分バックアップを取得
crontab および各スクリプトのイメージは次のようになります。
実際のスクリプトは古いバックアップの削除や通知など、運用のためにもう少し複雑な内容となっておりますが、ここでは今回の説明に絞って掲載します。
crontab(イメージ)
# 完全バックアップ
30 4 * * 6 root COMMAND=/commands/full_backup.sh
# 差分バックアップ
30 4 * * 1-5 root COMMAND=/commands/incremental_backup.sh
/commands/full_backup.sh(イメージ)
#!/bin/bash
SRC=/var/my-system/
SSH_TO=user@hostname
DEST=/backup/full/$(date "+%Y%m%d-%H%M%S")
rsync -a --delete -e ssh $SRC $SSH_TO:$DEST
/commands/incremental_backup.sh(イメージ)
#!/bin/bash
SRC=/var/my-system/
SSH_TO=user@hostname
DEST=/backup/incremental/$(date "+%Y%m%d-%H%M%S")
BASE=`ssh $SSH_TO "ls /backup/full/ | tail -n 1"`
rsync -a --delete -e ssh --link-dest=$BASE $SRC $SSH_TO:$DEST
-e ssh
を指定することでSSH経由で同期できます。なお、自動実行する場合はパスワード認証が使えないので、予め鍵登録を行う必要があります。
まとめ
本格的なバックアップソリューションを入れるまでもないけど、頻繁にバックアップをとりたい。とはいえ、ディスク容量は節約したい・・・。
そんなケースで便利な、 rsync を使ったバックアップ手法をご紹介しました。皆様のお役に立てれば幸いです。