web-dev-qa-db-ja.com

ZFS送信/受信に最適な圧縮

ポイントツーポイントのT1回線を介して増分ZFSスナップショットを送信していますが、次のバックアップが開始される前に、1日分のスナップショットをネットワーク経由でほとんど作成できない状態になっています。 send/recvコマンドは次のとおりです。

zfs send -i tank/vm@2009-10-10 tank/vm@2009-10-12 | bzip2 -c | \
ssh offsite-backup "bzcat | zfs recv -F tank/vm"

CPUサイクルには余裕があります。回線を介してより少ないデータをプッシュするために使用できるより良い圧縮アルゴリズムまたは代替方法はありますか?

15
Sysadminicus

最高の圧縮メカニズムをすべて試しましたが、回線速度によって制限されているようです。より高速な回線を実行することは問題外であると想定して、バックアップの実行頻度を減らして実行時間を増やすことを検討しましたか?

それ以外に、書き込まれるデータの量を減らす方法はありますか?アプリケーションスタックを知らなくても、その方法を言うのは難しいですが、新しいファイルを作成するのではなく、アプリが既存のファイルを上書きしていることを確認するなどの操作を行うと役立つ場合があります。また、不要な一時/キャッシュファイルのバックアップを保存しないでください。

2
semi

これは私があなたがやっていることとまったく同じことをやって学んだことです。 mbufferの使用をお勧めします。私の環境でテストするとき、それは受信側でのみ役立ちました。それなしでは、受信が追いつく間、送信が遅くなります。

いくつかの例: http://everycity.co.uk/alasdair/2010/07/using-mbuffer-to-speed-up-slow-zfs-send-zfs-receive/

オプションと構文のあるホームページ http://www.maier-komor.de/mbuffer.html

レプリケーションスクリプトからのsendコマンド:

zfs send -i tank/pool@oldsnap tank/pool@newsnap | ssh -c arcfour remotehostip "mbuffer -s 128k -m 1G | zfs receive -F tank/pool"

これにより、リモートホストでmbufferが受信バッファーとして実行されるため、送信ができるだけ速く実行されます。私は20メガビットの回線を実行しましたが、送信側にmbufferを設定しても効果がないことがわかりました。また、メインのzfsボックスはすべてのramをキャッシュとして使用しているため、1 gのmbufferでもキャッシュサイズを減らす必要があります。

また、これは本当に私の専門分野ではありません。sshに圧縮を任せるのが最善だと思います。あなたの例では、私はあなたがbzipを使用していて、デフォルトで圧縮を使用するsshを使用していると思うので、SSHは圧縮ストリームを圧縮しようとしています。暗号としてarcfourを使用することになりました。これは、CPU負荷が最も低く、それが私にとって重要であったためです。別の暗号を使用するとより良い結果が得られる可能性がありますが、SSHで圧縮を実行することをお勧めします(または、サポートしていないものを本当に使用したい場合は、ssh圧縮をオフにします)。

本当に興味深いのは、ローカルホストで送受信するときにmbufferを使用すると、速度も向上することです。

zfs send tank/pool@snapshot | mbuffer -s 128k -m 4G -o - | zfs receive -F tank2/pool

ローカルホスト転送用の4gが私にとってスイートスポットであるように見えました。これは、zfs send/receiveがレイテンシやストリーム内のその他の一時停止が本当にうまく機能しないことを示しているだけです。

私の経験だけで、これが役に立てば幸いです。これを理解するのにしばらく時間がかかりました。

9
aarontomosky

この質問が投稿されてから数年で状況は変化しました:

1:ZFSは圧縮レプリケーションをサポートするようになりました。-cフラグをzfs sendコマンドに追加するだけで、ディスク上で圧縮されたものは、パイプを通過してもう一方の端に渡されるときに圧縮されたままになります。 ZFSのデフォルトの圧縮はlz4であるため、さらに多くの圧縮が得られる可能性があります。

2:この場合に使用するのに最適なコンプレッサーはzstd(ZStandard)です。これは、圧縮レベル(サポートされている19以上のレベルと新しい高速zstd-fastレベルの間で)に基づいて圧縮レベルを変更する「アダプティブ」モードを備えています。 zfs sendとzfs recvの間のリンクの速度。パイプから出るのを待っているデータのキューを最小限に抑えながら、可能な限り圧縮します。リンクが高速であれば、データをさらに圧縮する時間を無駄にすることはありません。リンクが低速であれば、データをさらに圧縮し、最終的に時間を節約するために機能し続けます。また、スレッド圧縮もサポートしているため、gzipやbzipがサポートしていない複数のコアを、pigzipなどの特別なバージョンの外で利用できます。

2
Allan Jude

これはあなたの特定の質問に対する答えです:

rzip を試すこともできますが、compress/bzip/gzipとは少し異なる方法で機能します。

rzipはファイル全体を読み取ることができると想定しているため、パイプラインで実行することはできません。これにより、ローカルストレージの要件が大幅に増加し、バックアップを実行して1本のパイプでネットワーク経由でバックアップを送信することができなくなります。そうは言っても、少なくとも this テストによると、結果のファイルはかなり小さくなります。

リソースの制約がパイプである場合、バックアップを24時間年中無休で実行するため、スナップショットを絶えずコピーして、何とかしていくことを期待する必要があります。

新しいコマンドは次のようになります。

remotedir=/big/filesystem/on/remote/machine/
while 
  snaploc=/some/big/filesystem/
  now=$(date +%s)
  snap=snapshot.$now.zfssnap
  test -f $snaploc/$snap
do
  sleep 1
done

zfs send -i tank/vm@2009-10-10 tank/vm@2009-10-12 > $snaploc/$snap &&
rzip $snaploc/$snap &&
ssh offsite-backup "
        cat > $remotedir/$snap.rzip && 
        rzip -d $remotedir/$snap.rzip && 
        zfs recv -F tank/vm < $remotedir/$snap &&
        rm $remotedir/$snap " < $snaploc/$snap &&
rm $snaploc/$snap

あなたはより良いエラー修正を入れたいでしょう、そして、rsyncのようなものを使って圧縮ファイルを転送することを検討したいでしょう。転送が途中で失敗した場合、中断したところから再開できます。

2
chris

それが価値があるもののために。直接送信しない|圧縮|解凍|これを受信すると、転送ラインがスナップし、受信中にプールが長時間オフラインになると、受信側で問題が発生する可能性があります。ローカルファイルに送信してから、スナップショットをgzipしてrsync(riverbedを使用)で転送し、ファイルから受信します。転送に問題があり、河床を再起動する必要がある場合、河床は交通量を最適化しませんが、再送を高速化します。

Rsync圧縮を使用し、リバーベッド以外の圧縮を使用せずに、増分スナップショットを圧縮しないことを検討しました。どちらが良いかを言うのは難しいですが、rsync圧縮を使用してOracleからアーカイブログを転送する場合、転送速度はプレーンファイルおよびリバーベッド(RSyncを使用)のおよそ2倍になります。

リバーベッドがある場合、リバーベッドはsshではなくrsyncを使用します。これは、リバーベッドがrsyncを理解して最適化を試み、データをキャッシュに追加するためです(上記を参照して、転送を再開してください)。

1
freind

私の経験では、zfs sendは、次の圧縮ステップよりも(平均して)はるかに高速ですが、かなりバースト的です。バックアップにより、zfs sendの後にかなりのバッファリングが挿入され、gzipの後にさらにバッファリングが挿入されます。

zfs send $SNAP | mbuffer $QUIET -m 100M | gzip | mbuffer -q -m 20M | gpg ... > file

私の場合、出力デバイスはUSB(ネットワークではない)に接続されていますが、同様の理由でバッファリングが重要です。USBドライブが100%ビジー状態を保つと、全体のバックアップ時間が速くなります。 (要求どおりに)全体のバイト数を減らすことはできませんが、それでも早く終了することができます。バッファリングは、CPUバウンドの圧縮ステップがIOバウンドになるのを防ぎます。

1
Ben Jackson

WAN経由で送信するときは常にpbzip2を使用します(並列bzip2)。スレッド化されているため、-pオプションで使用するスレッド数を指定できます。最初に送信ホストと受信ホストの両方にpbzip2をインストールします。インストール手順は http://compression.ca/pbzip2/ にあります。

zfs send -i tank/vm@2009-10-10 tank/vm@2009-10-12 | pbzip2 -c | \
ssh offsite-backup "pbzip2 -dc | zfs recv -F tank/vm"

主なポイントは、スナップショットを頻繁な間隔(約10分)で作成して、スナップショットのサイズを小さくしてから、各スナップショットを送信することです。 sshは壊れたスナップショットストリームから再開しないため、送信する巨大なスナップショットがある場合は、ストリームをpbzip2にパイプし、管理可能なサイズのチャンクに分割し、rsyncでファイルを受信ホストに分割してから、連結したpbzip2ファイルをzfs recvにパイプします。

zfs send -i tank/vm@2009-10-10 tank/vm@2009-10-12 | pbzip2 -c | \
split -b 500M - /somedir/snap-inc-10-to-12.pbzip2--

これにより、500MBのチャンクで名前が付けられたファイルが生成されます。

/somedir/snap-inc-10-to-12.pbzip2--aa
/somedir/snap-inc-10-to-12.pbzip2--ab
/somedir/snap-inc-10-to-12.pbzip2--ac
...

rsyncを受信ホストに複数回(zfs送信が完了する前でも、完全な500MBチャンクが表示されるとすぐにでもrsyncできます)、いつでもctrl + cを押しますキャンセルします:

while [[ true ]]; do rsync -avP /somedir/snap-inc-10-to-12.pbzip2--* offsite-backup:/somedir ; sleep 1; done;

zfs receive:

cat /somedir/snap-inc-10-to-12.pbzip2--* | pbzip2 -dc | zfs recv -Fv tank/vm

ユーザーfreindは次のように述べています。直接送信しない|圧縮|解凍|これを受信すると、転送ラインがスナップし、受信中にプールが長時間オフラインになると、受信側で問題が発生する可能性があります。 -進行中の送信/受信がネットワークのドロップによって中断されたが、プールがオフラインにならない程度である場合、受信ホストで古いzfsバージョン28未満で以前に問題が発生しました。それは面白い。 「zfs recv」が受信側で終了した場合のみ、スナップショットを再送信します。必要に応じて、「zfs recv」を手動で強制終了します。 zfs send/recvがFreeBSDまたはLinuxで大幅に改善されました。

1
soyayix

私はあなたが単にあなたのサイトの生の帯域幅を増やすことができないと思います...

ホストで圧縮を使用しないことの利点がわかる場合があります。

Wanオプティマイザのようなものを使用する場合、送信する前にファイルを圧縮するしないファイルを転送すると、転送をより適切に最適化できます。パイプからのbzip2。バックアップを数回実行すると、WANオプティマイザは転送で見たものの非常に大きな部分をキャッシュし、転送速度が大幅に向上します。

あなたが限られた予算にいる場合、あなたはmay rsyncを使用してncompressedスナップショットをrsyncすることで同様の改善を見ることができます、すなわち:

zfs send -i tank/vm@2009-10-10 tank/vm@2009-10-12 > /path/to/snapshotdir/snapshotfile
rsync /path/to/snapshotdir/snapshotfile offsite-backup:/remote/path/to/snapshotfile
ssh offsite-backup 'zfs recv -F tank/vm < /remote/path/to/snapshotfile'

Rsyncは昨日のスナップショットと今日のスナップショットの違いのみを転送するため、これはより高速になります。スナップショットプロセスがどのように機能するかによっては、実際には同じファイルでなくても、2つの間に多くの冗長性がある場合があります。

Wanオプティマイザーは、この問題を解決するためのはるかに可能性の高い方法です(まあ、メトロイーサネットはこの問題を解決するためのmost可能性の高い方法ですが、ここでは省略します)。 rsyncは暗闇でのワイルドショットであり、ローカルデータに対してテストする価値があります(ローカルでは、rsyncは、ストレートコピーで節約された時間を教えてくれます)。

1
chris

-Dを使用してzfs sendの重複除去をオンにしてみてください。もちろん、節約量はデータの重複の程度によって異なります。

0
James Moore

データでテストする必要があります。ファイルに送信して、それぞれの方法で圧縮するだけです。

私たちにとって、gzipは大きな違いをもたらし、それをすべて実行しましたが、gzipとbzipまたは7zの間に1%の違いすらありませんでした。

遅いT1を使用している場合は、それをファイルに保存してrsyncする必要があります。

Lstvanのように帯域幅よりもCPUで少し制限されている(あなたではない)人々にとって、arcfour128のような別の暗号はスピードアップします。物事を移動するときに内部的に使用します。

0
Dan Buhler

あなたはsshおそらくblowfish-cbcのより速い暗号を拾うことができます、-123456789スイッチも試してください

-1 (or --fast) to -9 (or -best)
0
Istvan