前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >golang mongoDB GridFS查询 存储 删除文件

golang mongoDB GridFS查询 存储 删除文件

作者头像
地球流浪猫
发布2018-08-02 15:34:05
3.1K0
发布2018-08-02 15:34:05
举报
文章被收录于专栏:流浪猫的golang

先讲一下 GridFS的作用

GridFS 用于存储和恢复那些超过16M(BSON文件限制)的文件(如:图片、音频、视频等),如果没有超过16m大小可以将数据保存在BSON数据中。 GridFS 也是文件存储的一种方式,但是它是存储在MonoDB的集合中。

GridFS 会将大文件对象分割成多个小的chunk(文件片段),一般为256k/个,每个chunk将作为MongoDB的一个文档(document)被存储在chunks集合中。

GridFS 用两个集合来存储一个文件:fs.files与fs.chunks。 每个文件的实际内容被存在chunks(二进制数据)中,和文件有关的meta数据(filename,content_type,还有用户自定义的属性)将会被存在files集合中。 官方文档中还有这么两句话: GridFS is useful not only for storing files that exceed 16 MB but also for storing any files for which you want access without having to load the entire file into memory. See also When to Use GridFS. GridFS是可以存储任何你想要存储的文件,不仅仅是那些超过16M文件,意思是什么文件都能存。

Furthermore, if your files are all smaller the 16 MB BSON Document Size limit, consider storing the file manually within a single document instead of using GridFS. You may use the BinData data type to store the binary data. 此外,如果您的文件全部小于16 MB bson文档大小限制,请考虑将文件手动存储在单个文档中,而不是使用gridfs。您可以使用bindata数据类型来存储二进制数据。

第一步:先用命令行的方式存储一下,方便演示,我选一个音乐21M大小 在windows 的mongoDB安装平台下:与mongo.exe,mongod.exe 所在目录存在一个mongofiles.exe 命令行的方式进入,执行下面命令就可以:

代码语言:javascript
复制
mongofiles.exe -h 127.0.0.1  -d gridfs put Test.mkv

意思是向127.0.0.1的数据库gridfs添加Test.mkv 视频文件 参数说明: –d 指定数据库 ,默认是fs,Mongofiles list –d testGridfs -u –p 指定用户名,密码 -h 指定主机 -port 指定主机端口 -c 指定集合名,默认是fs -t 指定文件的MIME类型,默认会忽略 查看一下。 使用mongoDB的数据库工具“MongoDB Compass”查看数据

数据库中增加一个gridfs数据库,里面多了2个集合,分别为fs.chunks或者fs.files

打开fs.files可以看到数据库中有2个文件一个叫做something.mp3 一个Test.mkv,Test.mkv是我刚刚上传的。 上传的数据存在fs.chunks中,文件信息存储在fs.files中。

现在开始用golang代码操作了: 下载刚才存储的视频:还原到本地 。我选一个something.mp3 进行下载。 package main

代码语言:javascript
复制
import (
    "fmt"
    "gopkg.in/mgo.v2"

    "log"
    "os"
    "io"
)

func main() {
    session, err := mgo.Dial("mongodb://127.0.0.1:27017")
    defer session.Close()
    if err != nil {
        fmt.Println(err)
        return
    }
    names, err := session.DatabaseNames();
    if err != nil {
        fmt.Println("未查询到数据库名字:", err)
    }
    fmt.Println(names)
    //通过文件名获取mp3
    file, err := session.DB("gridfs").GridFS("fs").Open("someThing.mp3")
    if err !=nil {
        fmt.Println(err)
        return
    }
    out, _ := os.OpenFile("E:\\test\\something.mp3.", os.O_CREATE, 0666)
    _,err = io.Copy(out, file)
    check(err)
    err = file.Close()
    check(err)
    //
    //b := make([]byte, 8192)
    //n, err := file.Read(b)
    //check(err)
    //fmt.Println(string(b))
    //check(err)
    //err = file.Close()
    //check(err)
    //fmt.Printf("%d bytes read\n", n)
}
func check(err error){
    log.Print(err)
}

运行结果:可以直接将something.mp3 下载到本地。

保存上传操作: 将something.mp3 改名字为 my.mp3 保存到gridfs

代码语言:javascript
复制
func upload(){
    session, err := mgo.Dial("mongodb://127.0.0.1:27017")
    defer session.Close()
    if err != nil {
        fmt.Println(err)
        return
    }
    names, err := session.DatabaseNames();
    if err != nil {
        fmt.Println("未查询到数据库名字:", err)
    }
    fmt.Println(names)
    //通过文件名创建mp3
    file, err := session.DB("gridfs").GridFS("fs").Create("my.mp3")
    if err !=nil {
        fmt.Println(err)
        return
    }
    out, _ := os.OpenFile("E:\\test\\something.mp3.", os.O_RDWR, 0666)
    _,err = io.Copy(file, out)
    check(err)
    err = file.Close()
    check(err)
    err=out.Close()
    check(err)
}

运行结果

文件的删除操作

代码语言:javascript
复制
//直接利用名字移除
err = session.DB("gridfs").GridFS("fs").Remove("my.mp3")
    if err !=nil {
        fmt.Println(err)
    }else {
        fmt.Print("刪除成功")
    }

文件的查询操作

代码语言:javascript
复制
func ReadAll()  {
    session, err := mgo.Dial("mongodb://127.0.0.1:27017")
    defer session.Close()
    if err != nil {
        fmt.Println(err)
        return
    }
    names, err := session.DatabaseNames();
    if err != nil {
        fmt.Println("未查询到数据库名字:", err)
    }
    fmt.Println(names)
    //通过文件名获取mp3
    gfs := session.DB("gridfs").GridFS("fs");
    iter := gfs.Find(nil).Iter()

    result:=new(fileinfo)
    for iter.Next(&result) {
        fmt.Println("一个一个输出:", result)
    }

}
type fileinfo struct {
    //文件大小
    LENGTH int32
    //md5
    MD5 string
    //文件名
    FILENAME string
}

func check(err error){
    log.Print(err)
}

运行结果: 一个一个输出: &{3963133 e58d3babaa101a57876c4b59945dd274 someThing.mp3} 一个一个输出: &{68113996 f79616b9e7dab89c9a0985349fd3ad10 Test.mkv}

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018年04月14日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
对象存储
对象存储(Cloud Object Storage,COS)是由腾讯云推出的无目录层次结构、无数据格式限制,可容纳海量数据且支持 HTTP/HTTPS 协议访问的分布式存储服务。腾讯云 COS 的存储桶空间无容量上限,无需分区管理,适用于 CDN 数据分发、数据万象处理或大数据计算与分析的数据湖等多种场景。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档