GridFSは、MongoDB上にある単純なファイルシステムの抽象化です。 Amazon S3に精通している場合、GridFSは非常によく似た抽象概念です。では、なぜMongoDBのようなドキュメント指向データベースがファイルレイヤーの抽象化を提供するのでしょうか。いくつかの非常に正当な理由があることが判明しました:
-
ユーザーが生成したファイルコンテンツの保存
多数のWebアプリケーションを使用すると、ユーザーはファイルをアップロードできます。歴史的に、リレーショナルデータベースを操作する場合、これらのユーザー生成ファイルはデータベースとは別のファイルシステムに保存されます。これは多くの問題を引き起こします。必要なすべてのサーバーにファイルを複製するにはどうすればよいですか?ファイルが削除されたときにすべてのコピーを削除するにはどうすればよいですか?安全と災害復旧のためにファイルをバックアップする方法は? GridFSは、データベースと一緒にファイルを保存することでユーザーのこれらの問題を解決し、データベースのバックアップを利用してファイルをバックアップできます。また、MongoDBレプリケーションにより、ファイルのコピーが各レプリカに保存されます。ファイルの削除は、データベース内のオブジェクトを削除するのと同じくらい簡単です。
-
ファイルコンテンツの一部へのアクセス
ファイルがGridFSにアップロードされると、ファイルは256kのチャンクに分割され、個別に保存されます。したがって、ファイルの特定の範囲のバイトのみを読み取る必要がある場合は、ファイル全体ではなく、それらのチャンクのみがメモリに取り込まれます。これは、選択的に読み取ったり編集したりする必要のある大きなメディアコンテンツを処理する場合に非常に役立ちます。
-
MongoDBに16MBを超えるドキュメントを保存する
デフォルトでは、MongoDBドキュメントのサイズは16MBに制限されています。したがって、16 MBを超えるドキュメントがある場合は、GridFSを使用してそれらを保存できます。
-
ファイルシステムの制限の克服
多数のファイルを保存する場合は、ファイル/ディレクトリの最大数など、ファイルシステムの制限を考慮する必要があります。GridFSでは、ファイルシステムの制限について心配する必要はありません。また、GridFSとMongoDBシャーディングを使用すると、運用の複雑さを大幅に増すことなく、ファイルをさまざまなサーバーに分散できます。
GridFS –舞台裏
GridFSは2つのコレクションを使用してデータを保存します:
> show collections; fs.chunks fs.files system.indexes >
fs.filesコレクションにはファイルに関するメタデータが含まれ、fs.chunksコレクションには実際の256kチャンクが格納されます。シャーディングされたコレクションがある場合、チャンクは異なるサーバーに分散され、ファイルシステムよりもパフォーマンスが向上する可能性があります!
> db.fs.files.findOne(); { "_id" : ObjectId("530cf1bf96038f5cb6df5f39"), "filename" : "./conn.log", "chunkSize" : 262144, "uploadDate" : ISODate("2014-02-25T19:40:47.321Z"), "md5" : "6515e95f8bb161f6435b130a0e587ccd", "length" : 1644981 } >
MongoDBは、files_idとチャンク番号に複合インデックスを作成して、チャンクにすばやくアクセスできるようにします。
> db.fs.chunks.getIndexes(); [ { "v" : 1, "key" : { "_id" : 1 }, "ns" : "files.fs.chunks", "name" : "_id_" }, { "v" : 1, "key" : { "files_id" : 1, "n" : 1 }, "ns" : "files.fs.chunks", "name" : "files_id_1_n_1" } ] >
MongoDBGridFSの例
MongoDBには、GridFSシナリオの実行に役立つ「mongofiles」と呼ばれる組み込みユーティリティがあります。ドライバーでGridFSを使用する方法については、ドライバーのドキュメントを参照してください。
Put #mongofiles -h -u -p --db files put /conn.log connected to: 127.0.0.1 added file: { _id: ObjectId('530cf1009710ca8fd47d7d5d'), filename: "./conn.log", chunkSize: 262144, uploadDate: new Date(1393357057021), md5: "6515e95f8bb161f6435b130a0e587ccd", length: 1644981 } done! Get #mongofiles -h -u -p --db files get /conn.log connected to: 127.0.0.1 done write to: ./conn.log List # mongofiles -h -u -p list connected to: 127.0.0.1 /conn.log 1644981 Delete [root@ip-10-198-25-43 tmp]# mongofiles -h -u -p --db files delete /conn.log connected to: 127.0.0.1 done!
GridFSモジュール
MongoDBに保存されているファイルデータをウェブサーバーまたはファイルシステムから直接提供する場合は、いくつかのGridFSプラグインモジュールを利用できます。
- GridFS-Fuse –ファイルシステムへのGridFSのプラグイン
- GridFS-Nginx-Nginxから直接サーバーGridFSファイルへのプラグイン
GridFSの制限
-
ワーキングセット
データベースコンテンツと一緒にファイルを提供すると、メモリワーキングセットが大幅に混乱する可能性があります。ワーキングセットを邪魔したくない場合は、別のMongoDBサーバーからファイルを提供するのが最適な場合があります。
-
パフォーマンス
ファイル提供のパフォーマンスは、Webサーバーおよびファイルシステムからファイルをネイティブに提供するよりも遅くなります。ただし、追加された管理上の利点は、速度を落とす価値があるかもしれません。
-
アトミックアップデート
GridFSは、ファイルのアトミック更新を行う方法を提供していません。このシナリオが必要な場合は、ファイルの複数のバージョンを維持し、適切なバージョンを選択する必要があります。