野球ブログです!ヨシラバーさんが記載しています。

野球やエンターテイメントブログです。

プロ野球とエンターテイメントメディア(Yoshilover blog)ヨシラバー

yoshilover.com

大谷翔平の彼女・結婚の記事が人気のようです。ヨシラバーさんのメディアです。 yoshilover.com

rsyncの差分バックアップで!!

rsync差分バックアップするスクリプトなど
SSH
rsync

はじめに

レンタルサーバVPSを借りていると不意にデータが飛ぶことがたまにありますよね。 そんなときに備えて自宅サーバにリモートサーバのデータを差分でバックアップしておけると安心です。 有償/無償/商用も含めて様々なソリューションがあると思いますが、自分はお手軽にrsyncだけで実施しています。

方針

リモートのサーバAから、手元のサーバBにバックアップします。

リモートサーバA(IPアドレスaaa.bbb.ccc.ddd) [cron]リモートサーバA内のバックアップ対象データを /for_backup/ に集める 手元のサーバB [cron]rsyncで A:/for_backup/ を /remote_a_backup/latest に転送する [cron]rsyncで /remote_a_backup/latest を /remote_a_backup/YYYYMMDD に差分バックアップする スクリプト リモートサーバA内のバックアップ対象データを /for_backup/ に集める まあ適当に。

gather_for_backup.sh

!/bin/sh

rsync --progress -av --delete /etc /for_backup/ rsync --progress -av --delete /data /for_backup rsync --progress -av --delete /root/bin /for_backup/root rsync --progress -av --delete /var/lib/mysql /for_backup/var/lib ...

chown for rsync

chown -R takeuchi.rsync /for_backup rsyncで A:/for_backup/ を /remote_a_backup/latest に転送する rsync_from_remote_server.sh

!/bin/sh

rsync --progress -avz -e ssh --delete --bwlimit=150 takeuchi@aaa.bbb.ccc.ddd:/for_backup/ /remote_a_backup/latest rsyncで /remote_a_backup/latest を /remote_a_backup/YYYYMMDD に差分バックアップする rotation.sh

!/bin/sh

世代バックアップ

ROTATE_DAYS : LATEST_DIR を含めて何世代バックアップするか

ROTATE_DAYS=30 # BASEDIR=/remote_a_backup LATEST_DIR=${BASEDIR}/latest/ NEW_DIR=${BASEDIR}/date -d '-1 day' +%Y%m%d/ LINK_DIR=${BASEDIR}/date -d '-2 day' +%Y%m%d/ OLDEST_DIR=${BASEDIR}/date -d "-$ROTATE_DAYS day" +%Y%m%d/

rm -rf $OLDEST_DIR rsync -avz --progress --delete --link-dest=$LINK_DIR $LATEST_DIR $NEW_DIR crontab(ローカルサーバ) crontab 0 7 * * * /remote_a_backup/rsync_from_remote_server.sh > /tmp/a-backup-rsync.log; /remote_a_backup/rotation.sh > /tmp/a-backup-rotation.log 本当はもう少し異常系の処理が必要とは思いますけど 30 日以内に気づくという前提で。。

rsyncで公開鍵を指定してデータ転送する方法

ssh経由でrsyncを利用する際に、ssh鍵認証かつsshポート22以外に接続する方法。

コマンド

rsync -avz -e "ssh -p SSHポート番号 -i SSH秘密鍵ファイルパス" 送信元 username@hostname:~/dest/

例)
rsync -avz -e "ssh -p 2345 -i /c/sshkey/id_rsa" /c/develop/src/ hoge@192.168.1.10:~/dest/

公開鍵をリモート環境に保存、ローカルの秘密鍵とリモートの公開鍵で認証を行うので、ネットワーク上にパスワードが流れることがなく、セキュリティリを高めることができます。

ローカル側での設定

ローカルで秘密鍵と公開鍵のペアを生成し公開鍵をリモートに保存します。
リモートで鍵を生成し、秘密鍵をローカルに転送することも可能ですが、転送中に秘密鍵が漏れると、
公開鍵認証の意味がなくなってしまうので、ローカル側で生成したものを使用するようにします。

リモートのユーザー名 : hoge
リモートのホスト名 : example.com
リモートのディレクトリ名 : /home/hoge/
リモートのSSHポート番号 : 20022
ローカル側で秘密鍵と公開鍵のペアを生成
$ ssh-keygen -t rsa
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa): #「Enter」を押す
Enter passphrase (empty for no passphrase): # 秘密鍵パスフレーズを入力
Enter same passphrase again: # もう一度

他のユーザーに見られないようにパーミッションを変更

$ chmod 600 .ssh/id_rsa

リモートに公開鍵を転送

$ scp -P 20022 .ssh/id_rsa.pub hoge@example.com:/home/hoge/.ssh/
hoge@example.com's password: # リモートのパスワードを入力

リモート側での設定

他のユーザーに見られないようにパーミッションを変更(未設定の場合)
$ chmod 700 .ssh
$ chmod 600 .ssh/authorized_keys
転送されてきた公開鍵をリネーム
$ mv .ssh/id_rsa.pub .ssh/authorized_keys
既に他のホストの公開鍵が設定されている場合はリネームでなく追記する
$ cat .ssh/id_rsa.pub >> .ssh/authorized_keys
$ rm .ssh/id_rsa.pub

ついでにrsyncを使う場合の方法も記しておきます。rsyncはファイルやディレクトリを転送するためのコマンドです。リモートのファイルやディレクトリをローカルに転送したり、ローカルのファイルやディレクトリをリモートに転送することができるので、バックアップ作業を行うときに活躍します。

書式 : rsync [オプション] 転送元 転送先
ローカルのファイルをリモートに転送する場合
ローカルのディレクトリ : /home/backup/backup.gzip
リモートのユーザ名 : hoge
リモートのホスト名 : example.com
リモートの転送先ディレクトリ : /home/hoge/backup/
$ rsync -avz /home/backup/backup.gzip hoge@example.com:/home/hoge/backup/
ポート番号が標準の22以外の場合
$ rsync -avze "ssh -p ポート番号" /home/backup/backup.gzip hoge@example.com:/home/hoge/backup/

Linux 蓄積されていくログディレクトリなどを定期的に削除する例(findを利用)

findを利用して、30日以前のディレクトリを削除する方法を示します。

Delete old data.

1). aaa フォルダ配下の30日以上前のディレクトリを backup フォルダへ移動 find ./aaa -type d -mtime +30 | xargs mv --target-directory=./backup

2).30日以上前のディレクトリを強制削除 find . -type d -mtime +30 | xargs rm -fr

危険なので、2)が望ましいとは思います

ファイルを消しても消えないことがある!!

なんでこうなるのか? Linux/Unixでは、ls/find等で一覧表示されなくてもプロセスがつかんでいる状況では 実際にはファイルシステムから削除されておらず、見えなくなる。 OSを再起動するとファイルシステム使用量が減るのは、表面上は見えないくプロセスが つかんでいるファイルを再起動によるプロセスにより、開放してくれる。

このような現象はプログラムバグでファイルクローズのしわすれ等の場合に発生する ことがあります。

対応方法 †

このようなとき以下ように lsof コマンドでどのプロセスがつかんでいるか確認し、 そのプロセスを終了(kill)させることで対応できます。

$ df -k . Filesystem 1K-ブロック 使用 使用可 使用% マウント位置 /dev/sdb1 988212 115412 822600 13% /mnt/sdb1
find . -ls
2 4 drwxr-xr-x 3 root root 4096 1月 19 14:54 .
11 16 drwx------ 2 root root 16384 1月 19 13:55 ./lost+found
$ lsof | grep /mnt/sdb1
bash 1910 root cwd DIR 8,17 4096 2 /mnt/sdb1
fileopen. 1932 root 3r REG 8,17 100000000 12 /mnt/sdb1/testfile.dat (deleted)
lsof 1938 root cwd DIR 8,17 4096 2 /mnt/sdb1
grep 1939 root cwd DIR 8,17 4096 2 /mnt/sdb1
lsof 1940 root cwd DIR 8,17 4096 2 /mnt/sdb1
$ ps auxww | grep 1932 | grep -v grep
root 1932 0.0 0.2 6664 1520 pts/0 S+ 14:54 0:00 /usr/bin/perl /root/fileopen.pl
kill 1932
$ find . -ls
2 4 drwxr-xr-x 3 root root 4096 1月 19 14:54 .
11 16 drwx------ 2 root root 16384 1月 19 13:55 ./lost+found