Docs 菜单
Docs 主页
/ / /
Ruby MongoDB 驱动程序
/

GridFS

在此页面上

  • 创建 GridFS 对象 ("Grid::FSBucket")
  • 使用写入流
  • 使用读取流
  • 查找文件元数据
  • 删除文件
  • 使用 Grid::文件 对象
  • 插入文件
  • 查找文件
  • 删除文件

该驱动程序提供了一个干净简单的接口来处理数据库中数据块文件的存储,也称为“GridFS”模式。该 API 允许您使用 Grid::文件 对象或读取和写入流。

您可以通过在数据库上调用 fs (使用可选参数)来创建 GridFS 对象。 fs会返回一个Grid::FSBucket对象。

Grid::FSBucket支持的选项包括:

选项
说明
:bucket_name
GridFS 存储桶的名称。 默认值为fs
:fs_name
GridFS 存储桶的名称。 优先于bucket_name 。 默认值为fs
:chunk_size
指定数据库中每个文件数据块的大小。
:write_concern
上传文件时使用的写关注(write concern)。 有关如何使用写入关注,请参阅 CRUD操作下的 写关注 部分。
:write
已弃用。 与:write_concern相同。
:read
下载文件时使用的读取偏好(read preference)。

例如,您可以创建具有特定读取偏好(read preference)的 GridFS 存储桶对象:

fs_bucket = database.fs( read: { mode: :secondary } )

要使用写入流将文件上传到 GridFS,您可以打开一个流并直接向其写入,或者将IO对象的全部内容一次性写入 GridFS。

要打开上传流并写入,请执行以下操作:

File.open('/path/to/my-file.txt', 'r') do |file|
fs_bucket.open_upload_stream('my-file.txt') do |stream|
stream.write(file)
end
end

要在一次调用中上传 IO 对象的全部内容:

File.open('/path/to/my-file.txt', 'r') do |file|
fs_bucket.upload_from_stream('my-file.txt', file)
end

写入流支持以下选项:

选项
说明
:chunk_size
指定数据库中每个文件数据块的大小。
:write_concern
上传文件时使用的写关注(write concern)。有关如何使用写关注(write concern),请参阅CRUD下的写关注(write concern)部分。
:write
已弃用。 与:write_concern相同。

这些选项可以作为写入流方法的最后一个参数提供:

fs_bucket.open_upload_stream('my-file.txt', write_concern: {w: 2}) do |stream|
stream.write_concern
# => #<Mongo::WriteConcern::Acknowledged:0x46980201422160 options={:w=>2}>
# ...
end
fs_bucket.upload_from_stream('my-file.txt', file, write_concern: {w: 2})

要使用读取流从 GridFS 下载文件,您可以打开读取流并直接从中读取,也可以一次下载整个文件。

要打开下载流并从中读取数据,请执行以下操作:

File.open('/path/to/my-output-file.txt', 'w') do |file|
fs_bucket.open_download_stream(file_id) do |stream|
file.write(stream.read)
end
end

要一次性下载所有文件并将其写入 IO 对象:

File.open('/path/to/my-output-file.txt', 'w') do |file|
fs_bucket.download_from_stream(file_id, file)
end

您还可以下载由名称和(可选)修订号指定的文件。 修订号用于区分同名的文件,按上传日期排序。 传递给open_download_stream_by_name的修订版本号可以是正数,也可以是负数。

File.open('/path/to/my-output-file.txt', 'w') do |file|
fs_bucket.open_download_stream_by_name('my-file.txt', revision: -2) do |stream|
file.write(stream.read)
end
end

要下载由名称和(可选)修订号指定的文件的全部内容:

File.open('/path/to/my-output-file.txt', 'w') do |file|
fs_bucket.download_to_stream_by_name('my-file.txt', file, revision: -2)
end

读取流支持以下选项:

选项
说明
:read
下载文件时使用的读取偏好(read preference)。

上面列出的部分(但不是全部)读取方法会将这些选项传递给底层读取流。 请查阅每种方法的 API 文档,以确定它是否支持特定选项。

您可以检索包含 GridFS 文件collection中文件元数据的文档。

fs_bucket.find(filename: 'my-file.txt')

您可以通过 id 删除文件。

fs_bucket.delete(file_id)

此对象可用于包装要使用 GridFS 插入数据库的文件以及检索的对象。

要使用原始数据创建文件:

file = Mongo::Grid::File.new('I am a file', :filename => 'new-file.txt')

要从 Ruby File对象创建文件:

file = File.open('/path/to/my-file.txt')
grid_file = Mongo::Grid::File.new(file.read, :filename => File.basename(file.path))

要更改文件选项(例如数据块大小),请将选项传递给构造函数:

file = File.open('/path/to/my-file.txt')
grid_file = Mongo::Grid::File.new(
file.read,
:filename => File.basename(file.path),
:chunk_size => 1024
)

以下是文件支持的可用选项的完整列表。

选项
说明
:chunk_size
设置数据库中每个文件数据块的大小。
:content_type
设置文件的内容类型。
:filename (必需)
文件名。
:upload_date
文件上传(存储)的日期。

可以一次将一个文件插入数据库。 默认情况下,文件数据块插入到fs.chunkscollection中,文件元数据插入到fs.filescollection中。

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
file = Mongo::Grid::File.new('I am a file', :filename => 'new-file.txt')
client.database.fs.insert_one(file)

要插入到名称前缀不是fs的collection中,请使用:fs_name选项访问文件系统。

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
file = Mongo::Grid::File.new('I am a file', :filename => 'new-file.txt')
client.database.fs(:fs_name => 'grid').insert_one(file)

当驱动程序将第一个文件插入存储桶时,它将尝试在fileschunkscollection上创建所需的索引。所需的索引如下:

# files collection
{ :filename => 1, :uploadDate => 1 }
# chunks collection
{ :files_id => 1, :n => 1 }, { :unique => true }

注意

如果无法创建索引(例如由于当前用户没有创建索引的权限),则文件插入操作将中止。 如果应用程序没有创建索引的权限,数据库管理员必须提前创建所需的索引。

如果存储桶中已有文件,则驱动程序不会尝试创建索引,即使这些文件缺失且当前用户有权创建这些文件。 在这种情况下,数据库管理员应尽快创建所需的索引,以确保数据的完整性。

还可以对文件进行流式传输,作为直接插入的替代方法。

client.database.fs.open_upload_stream(filename) do |stream|
stream.write(file)
end

要从数据库检索文件,请使用适当的筛选器调用find_one

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
client.database.fs.find_one(:filename => 'new-file.txt') # Returns a Mongo::Grid::File

还可以流式传输文件,作为直接查找的替代方法。

client.database.fs.open_download_stream(file_id) do |stream|
io.write(stream.read)
end
fs.download_to_stream(file_id, io)

要删除文件,请将文件对象传递给delete_one

client = Mongo::Client.new([ '127.0.0.1:27017' ], :database => 'music')
fs = client.database.fs
file = fs.find_one(:filename => 'new-file.txt')
fs.delete_one(file)

后退

查询缓存