1 GridFS简介

  当前Bson能存储的最大尺寸是16M,我们想把大于16M的文件存入mongoDB中怎么办呢?mongoDB提供的GridFS就是专门做这个的。使用GridFS存储大文件时,文件被分成一个个的块(默认大小是255 kb),将每一块存放在一个单独的document中。GridFS将文件存储在两个collection中:chunks collection和files collection,其中chunks collection保存文件块,files collection保存文件的元数据。

2 使用mongofiles进行大文件管理

  mongofiles是mongoDB内置的文件操作工具,提供了十分简单的API让我们可以通过命令行实现文件的上传、下载、查找和删除。我们使用一个视频文件做测试。

1 上传文件(put)

  这里准备将/data/videos下的电影绿皮书(文件名:”lvpishu.mkv“)上传到mongoDB数据库myfiles中下,只需要使用一条命令就可以完成文件的上传:在mongoDb的bin目录下执行命令   mongofiles -d myfiles -l /data/videos/lvpishu.mkv put lvpishu.mkv ----host 192.168.70.131:27017  ,如果标明--host的话默认上传到localhost。上传完成后使用robomongo查看文件信息,如下:

  使用robomongo查看上传的文件信息,如下图:

2 下载文件(get)

  下载GridFS中的文件使用命令Get,如我们要将刚才上传的电影,下载到/data/videos2目录下,执行命令 mongofiles -d myfiles -l /data/videos2/lvpishu.mkv get lvpishu.mkv 即可,效果如下:

3 查找文件(list、search)

  查询 GridFS中的文件可以使用search查询文件名包含某字符串的文件信息,使用list查询以某字符串开头的文件列表,因为我们只上传了一个文件所以这里的文件列表也只展示一条文件信息,执行命令效果如下:

4 删除文件(delete)

  如果我们想删除GridFS中的某一文件,使用delete <filename>命令

3 使用C#驱动操作GridFS

  前边我们已经使用mongoDB自带的命令行工具mongofiles实现了大文件的增删查操作,但是实际开发中我们更常用的方式是使用各种语言驱动来管理文件,这里展示怎么通过C#驱动来实现大文件的管理。添加GridFS的包 Install-Package MongoDB.Driver.GridFS ,C#驱动中提供了GridFSBucket(GridFS桶)对象来保存文件,它是fs.files和fs.chunks的组合,我们在使用时,最好使用GridFSBucket来和GridFS交互,尽量不要直接使用底层的fs.files和fs.chunks)。

  C#驱动mongoDB的上传和下载文件有两种形式:①通过字节数组byte[]上传和下载,这种方式适用于文件不大的情况,②使用stream的方式进行上传和下载,这种形式适用于各种场合,这里就采用stream的形式做文件的上传和下载演示,代码如下:

    class Program
{
static void Main(string[] args)
{
//连接数据库
var client = new MongoClient("mongodb://192.168.70.133:27017, 192.168.70.131:27017, 192.168.70.129:27017");
//获取database
var mydb = client.GetDatabase("myfilesDb");
//初始化GridFSBucket
var bucket = new GridFSBucket(mydb, new GridFSBucketOptions
{
BucketName = "lvpishu", //设置根节点名
ChunkSizeBytes = * , //设置块的大小为1M
WriteConcern = WriteConcern.WMajority, //写入确认级别为majority
ReadPreference = ReadPreference.Secondary //优先从从节点读取
});
//上传文件
//上传的配置项,可以添加文件元数据
var options = new GridFSUploadOptions
{
//ChunkSizeBytes = 1048000,
Metadata = new BsonDocument
{
{ "format", "mkv" },
{ "country", "USA" }
}
};
//通过stream形式上传文件
ObjectId fileId;
Console.WriteLine("开始文件上传---------------->");
string sourceFile = @"D:\迅雷下载\lvpishu.mkv";
using (var fs = new FileStream(sourceFile, FileMode.Open))
{
//mongodb中的文件名为“绿皮书”
Console.WriteLine("上传中...");
fileId = bucket.UploadFromStream(filename: "绿皮书", source: fs, options: options);
}
Console.WriteLine("<----------------文件上传完成");
Console.WriteLine(); //查看文件
var filter = Builders<GridFSFileInfo>.Filter; using (var cursor = bucket.Find(filter.Eq(x => x.Filename, "绿皮书")))
{
var fileInfo = cursor.FirstOrDefault();
fileId = fileInfo.Id;
Console.WriteLine($"文件名:{fileInfo?.Filename}, 文件大小:{fileInfo?.Length}字节, 文件上传时间:{fileInfo?.UploadDateTime.AddHours(8)}");
Console.WriteLine($"自定义的元数据:{fileInfo?.Metadata}");
}
Console.WriteLine(); //下载文件
//文件下载的位置
Console.WriteLine("开始文件下载---------------->");
string tagrgetPath = @"D:/mongoDownLoad/绿皮书下载.mkv";
using (var mongoStream = bucket.OpenDownloadStream(id: fileId))
{
Console.WriteLine("下载中...");
//通过FileStream写文件
using (FileStream fsWrite = new FileStream(tagrgetPath, FileMode.Create))
{
//开辟临时缓存内存
byte[] buffer = new byte[ * ];
while (true)
{
//readCount是真正读取到的字节数
int readCount = mongoStream.Read(buffer, , buffer.Length);
//写入目标文件
fsWrite.Write(buffer, , readCount);
//判断是否读取完成
if (readCount < buffer.Length)
{
break;
}
}
}
}
//最好比较一下mongodb中的文件和下载文件的Md5值,如果md5相同表示下载完成
//这里为了简单起见,就简单判断以下文件是否存在
if (File.Exists(@"D:/mongoDownLoad/绿皮书下载.mkv"))
{
Console.WriteLine("<----------------文件下载完成!");
}
Console.WriteLine(); //删除文件
bucket.Delete(id: fileId);
Console.WriteLine("文件已删除!"); Console.ReadKey();
}
}

  初始化GridFSBucket时可以设置一些参数:BucketName用于设置files和chunks的根节点名,如设置BucketName="lvpishu",那么在数据库中保存文件的两个collection的名字为lvpishu.files和lvpishu.chunks。ChunkSizeBytes用于设置数据块的大小,这里设置数据块大小为1M。

代码的注释比较详细,这里就不多介绍了,程序运行结果如下:

小结   

  本节介绍了GridFS的概念,并简单演示了怎样使用mongofile和C#驱动进行大文件的上传、查询、下载、删除操作。如果文中有错误的话,希望大家可以指出,我会及时修改,谢谢!

  

快速掌握mongoDB(五)——通过mongofiles和C#驱动操作GridFS的更多相关文章

  1. 快速掌握mongoDB(五)——读写分离的副本集实现和Sharing介绍

    1 mongoDB副本集 1 副本集简介 前边我们介绍都是单机MongoDB的使用,在实际开发中很少会用单机MongoDB,因为使用单机会有数据丢失的风险,同时单台服务器无法做到高可用性(即当服务器宕 ...

  2. MongoDB基础入门003--使用官方驱动操作mongo,C#

    本篇先简单介绍一下,使用官方驱动来操作MongoDB.至于MongoDB原生的增删改查语句,且等以后再慢慢学习. 一.操作MongoDB的驱动主要有两个 1.官方驱动:https://github.c ...

  3. MongoDB五种树形结构表示法

    MongoDB五种树形结构表示法 第一种:父链接结构 db.categories.insert( { _id: "MongoDB", parent: "Databases ...

  4. 《Effective C#》快速笔记(五)- - C# 中的动态编程

    静态类型和动态类型各有所长,静态类型能够让编译器帮你找出更多的错误,因为编译器能够在编译时进行大部分的检查工作.C# 是一种静态类型的语言,不过它加入了动态类型的语言特性,可以更高效地解决问题. 一. ...

  5. 带你快速了解 MongoDB 分布式集群

    在分布式应用系统中,mongodb 已经成为 NoSQL 经典数据库.要想很好的使用 mongodb,仅仅知道如何使用它是不够的.只有对其架构原理等有了充分认识,才能在实际运用中使其更好地服务于应用, ...

  6. 快速掌握mongoDB(四)—— C#驱动MongoDB用法演示

    前边我们已经使用mongo shell进行增删查改和聚合操作,这一篇简单介绍如何使用C#驱动MongoDB.C#驱动MongoDB的本质是将C#的操作代码转换为mongo shell,驱动的API也比 ...

  7. [置顶] 使用mongofiles操作GridFS

    使用mongofiles操作GridFS GridFS描述: GridFS,看起来像一种文件系统,其实是一种数据库用法.主要用来在数据库中存储二进制大文件.可以统一用数据库处理数据,而无需借助外部的文 ...

  8. 使用MongoDB C#官方驱动操作MongoDB

    想要在C#中使用MongoDB,首先得要有个MongoDB支持的C#版的驱动.C#版的驱动有很多种,如官方提供的,samus. 实现思路大都类似.这里我们先用官方提供的mongo-csharp-dri ...

  9. C#中使用官方驱动操作MongoDB

    想要在C#中使用MongoDB,首先得要有个MongoDB支持的C#版的驱动.C#版的驱动有很多种,如官方提供的,samus. 实现思路大都类似.这里我们先用官方提供的mongo-csharp-dri ...

随机推荐

  1. 栈内存不是只有2M吗?为什么不溢出?

    #include <stdio.h> #include <wchar.h> #include <stdlib.h> #define MAX_PATH 1024 FI ...

  2. Qt 5.3更新无数,更改C++控制台输出最为赞(这样就和普通C++ IDE没区别了)

    转载请注明文章:Qt 5.3更新无数,更改C++控制台输出最为赞 出处:多客博图 本人觉得有了这个更新,Qt Creator可谓几乎没有缺点了,起码仅仅开发C/C++,是不用再去安装VS了. Qt 5 ...

  3. 减少Qt编译时间暨简单Qt裁剪

    本站所有文章由本站和原作者保留一切权力,仅在保留本版权信息.原文链接.原文作者的情况下允许转载,转载请勿删改原文内容, 并不得用于商业用途. 谢谢合作.原文链接:减少Qt编译时间暨简单Qt裁剪 编译一 ...

  4. 使用Hibernate连接Oracle 无法识别生成的SQL问题

    问题: 在JAVA工程中,数据库使用的是OracleXE(Oracle10g Express Edition). 使用hibernate.reveng.xml创建了实体类及其DAO类,如: tt.my ...

  5. JVM底层实现与总结

    一.类加载器 1.BootstrapClassLoader(启动类加载器) 它主要负责加载%JAVA_HOME%/jre/lib,-Xbootclasspath参数指定的路径以及%JAVA_HOME% ...

  6. Spring Cloud Stream整合RabbitMQ

    简介 Spring Cloud Stream是一个构建消息驱动微服务的框架,应用程序通过input(相当于consumer).output(相当于producer)来与Spring Cloud Str ...

  7. php7中异常

    php7中新增异常错误处理 在PHP7之前的版本,对于一些错误异常是没有办法捕获的. php7中新增throwable接口,可以用来捕获一些错误 Exception,Error这实现了Throwabl ...

  8. Spring 之Aop实现日志记录

    Aop实现见代码,简单demo实现 package com.idcos.automate.config; import com.idcos.automate.dal.auto.dao.dcos.Dco ...

  9. iOS开发系列之性能优化(上)

    本篇主要记录一下我对界面优化上的一些探索.关于时间优化的探索将会在中篇里进行介绍.下篇将主要介绍一些耗电优化.安装包瘦身的探索. ### 1.卡顿原理 要了解卡顿原理,需要对帧缓冲区.垂直同步.CPU ...

  10. .NET Core IdentityServer4实战 第Ⅴ章-单点登录

    OiDc可以说是OAuth的改造版,在最初的OAuth中,我们需要先请求一下认证服务器获取下Access_token,然后根据Access_token去Get资源服务器, 况且OAuth1 和 2 完 ...