Topface写真ストレージは現在オープンソースです

私たちは写真を保存するのが得意なので、独自のtumblr、facebook、imgurを構築したい場合、あなたの生活を楽にすることを決めました。 問題は実際には単純ですが、事前に最もよく知られている微妙な点があります。 さらに、 node.jsすべてを行いました 。これは、100,000,000枚以上の写真があるリポジトリではあまり一般的ではありません。



画像



オープンソースでは、ディスクと直接やり取りするインフラストラクチャの部分を放棄することにしました。 残りはnginxによって制御され、その改善はすでにメインのnginxブランチ(image_filterモジュールのプログレッシブjpegおよびその変数のサポート)で行われるか、nginx-develメール送信のウィングで待機します(トリミング中に画像の特定のエッジに「貼り付く」可能性) 。



リポジトリは、写真だけでなく、無限の寿命を迎える可能性があり、有限でかなり小さなサイズのデータ​​にも適しています。 ビデオなどの大量のデータを保存することは、単純にファイルシステムに保存することで、より簡単で収益性が高くなります。 データは不変でなければなりません。 写真にフィルターを適用した場合は、新しい名前で保存します。



インフラストラクチャ全体に単一障害点はありません。そのため、s石をいくつかのサーバーに入れることは問題ではありません。 ディスクは私たちが望むよりもはるかに頻繁にバラバラになるので、そのような機能は最初から置かれていました。



コンポーネントについて簡単に説明します。



バックパックコーディネーター



GitHubへのリンク 。 ここでは、システム全体を展開する方法を学ぶことができます。



コーディネーター-アプリケーションがストアにデータを保存するために通信するレベル。 コマンド可能:







コーディネーターインスタンスは同等で互換性があり、データシャーディングを管理し、zookeeperを介して通信します。 彼らは次の写真をどこに置くかを知っています。 シャード内のインスタンスの数によって、データコピーの数、シャードの数、およびそれらのサイズ(ストレージの合計サイズ)が決まります。



シャード-同じデータセットを共有する複数のバックパックインスタンス。



写真がストレージにアップロードされると、シャードの1つのインスタンスに保存され、その後、シャードの他のインスタンスへのレプリケーション用のタスクが作成されます。 異なる物理マシン上のシャードごとに3つのバックパックインスタンスがあるため、met石が1つのサーバーに落ちた場合でも、シャードは機能し続けます。



不要な移動を行わないように最善を尽くしているため、リポジトリに新しいシャードを追加する際に再調整は行われないことに注意してください。 新しいシャードにもっと積極的に書き込みます。 これは、リバランスが難しい(実際にはい)ことも、マスターしていない(実際にマスターした後、心を変えた)ためでもありませんが、実際には必要ではありません。



バックパックレプリケーター



GitHubへのリンク



複製レベル。これは、バックパックインスタンスの画像を分解するだけです。 アクセスできないインスタンスは、起動後にデータを取得します。 zk-redis-queueモジュールを使用して、メッセージの処理を少なくとも1回保証します。



また、レプリケーターインスタンスは互換性があり、ピアであるため、負荷に応じてインスタンスを実行できます。



バックパック



GitHubへのリンク



データストレージのレベル、ストレージのまさに塩。 webdav(GET、PUT)をコマンドできます:







必要に応じて、nginxはwebdavモジュールまたはwebdavで実行可能なものに置き換えることができます。 十分なnginxがなかったため、自分でバックパックを作成する必要がありました。 写真を保存するFacebookの干し草の山に触発されました。 Haystackは閉鎖的な開発であることが判明しましたが、それにはホワイトペーパーがあり、そこから貴重な知識が収集されました。



バックパックの本質は、インデックスを完全にメモリ(redis)に保存し、多くの小さなファイルを大きなファイルに書き込むことです。 したがって、ファイルを読み取るには、インデックスからデータ(オフセットと長さ)を取得し、1つのpreadを作成するだけです 。 写真のメタデータに関する情報(ファイルの権利など)を取得する必要はなく、単一のディスク内のデータをシークします。 とりわけ、O_DIRECTを使用してディスク上の読み取り値を均等にします。これにより、生産性に数パーセントのボーナスが与えられます。



nginxと比較したバックパックの利点は、テストで理解できます。 1,700,000枚のランダムな写真を撮り、同じサーバー上のバックパックとnginxに保存しました。 100,000個のランダムファイルを選択し、20個のストリームで読み取ることにしました。



赤い線はバックパック、緑の線はnginxです。



1秒あたりのリクエスト


画像



バックパックはすべてについて約732秒かかりましたが、nginxは1200秒で、差は33%です。



1秒あたりのディスク読み取り


画像



ここで、nginxがディスクからより多くの読み取りを行い、ディスクヘッドをより多く動かし、この操作が無料ではない理由が明らかになります。 時間の経過とともに、nginxはディスクキャッシュをメタデータで満たし、高速化しますが、これでも十分ではありません。 さらに多くのデータがある場合、nginxはディスクキャッシュに入る可能性がさらに低くなります。 さらに多くのデータがあります。



I / Oの使用


画像



私があなたをだましていると思わないように、i / oグラフでは、各オプションが常にディスクを100%使用していることが明らかです。



すべてのプロジェクトはnode.js 0.10をサポートしており、リークしていないようです。少なくともヒープは数週間作業しても一定のままです。 私たちは月を通して悪魔を始めます。



自宅でバックパックスタックを拡張することにした場合は、喜んでいます!



All Articles