mysqldumpやtarでサイトのバックアップを取得することはよくあると思います。
実データと同じサーバに保存しておけば操作ミスのリカバリーに有用ですが、それだとサーバのデータが飛んでしまうとどうしようもないので、バックアップは実データとは別のストレージにするのが鉄則です。
とはいえ念のためサーバ内にもバックアップが欲しい!というときには、少し工夫すると1コマンドでサーバとリモートに同時にバックアップを保存することができます。
数サイトくらいでは同時に実行せずとも良いのですが、多数あるとそれなりに所要時間が違ってきて役に立ちます。
さらに、今回はバックアップの所要時間を減らしたいというケースに遭遇したので、この機会にパターンをいくつか用意してコマンドと所要時間を比較してみました。
ここでは、AWS S3をリモートの保存先とした例を記載します。
mysqldump
mysqldump は出力先がstdoutなので、ファイルとして保存する際にはリダイレクトを利用します。
合わせて gzip で圧縮してあげると容量が節約されていい感じです。
mysqldump --defaults-extra-file=${HOME}/.mysql/login ${DB_NAME} | gzip | tee ${DB_NAME}.sql.gz | aws s3 cp - s3://${BUCKET}/${FOLDER}/${DB_NAME}.sql.gz
ポイントは、 tee
でデータの流れ先をファイルとstdoutに分岐させるところになります。
aws s3 コマンドがストリームをソースとして使えるところもありがたいですね。
tar
tar についても、fオプションを使わなければ出力先は stdout になりますので、その後は mysqldump と同様に扱えます。
tar cz ${DIR_NAME} | tee ${DIR_NAME}.tar.gz | aws s3 cp - s3://${BUCKET}/${FILDER}/${DIR_NAME}.tar.gz
(おまけ) 所要時間の最適化について
12GBのディレクトリ test を圧縮してローカルに保存し、かつS3にも保存するケースでコマンド別に完了までの所要時間を比較します。
Command 1. tarでフォルダを1ファイルに圧縮して保存し、その後S3にもコピー
tar czf test.tar.gz test/ && aws s3 cp test.tar.gz s3://${BUCKET}/test.tar.gz
よく使われるケースと思います。この所要時間を基準とします。
所要時間: 10m 19s
Command 2. tarの圧縮とs3へのコピーをワンライナーで実行
tar cz test/ | tee test.tar.gz | aws s3 cp - s3://${BUCKET}/test.tar.gz
所要時間: 9m 54s
1ファイルでは思ったほどの差異はありませんでしたが、Command 2.の方はCPU使用率が低く抑えられており、並列で複数フォルダを同時実行するのにも耐えうる状況でした。
一方で Command 1. の方は tar 実行時にCPUをフルに使っており、処理の並列化はやや難しそうでした。
Command 3. gzipのレベルを調整
tar c test/ | gzip -v4 | tee test.tar.gz | aws s3 cp - s3://${BUCKET}/test.tar.gz
所要時間: 6m 23s
gzipを個別に実行し、かつ圧縮レベルを4に落とした例も確認しました。
速度は大幅に向上し、圧縮後のサイズは 3.5GB -> 3.6GB へと増えましたが多くの場合にて許容範囲となりそうです。
結果のまとめ
以下の結果となりまして、圧縮レベルもそれなりで所要時間の短いCommand 3.を採用することにしました。
なお7zipやbzipも試してみたのですが、圧縮レベルの割に所要時間が激増したので利用は難しかったです。用途次第ですね。
Command 1. | Command 2. | Command 3. |
---|---|---|
10m 19s | 9m 54s | 6m 23s |