MongoDB 使用 Gridfs 在用户 collection 中保存图像

MongoDB save images in user collection with Gridfs

目前我正在使用 Scala 开发带有 Play 2 Framework 的后端服务器。 我有以下问题:

我使用文件处理程序 GridFS 在 MongoDB 中保存图像等文档。 GridFs 创建两个文件:

fs.files,其中包含元数据和 fs.chunks,存储块

但我想将图像保存在我自己的 collection 中。所有图像都应该有一个数据库条目,如用户名和评论。 我有两个解决问题的想法,但我需要帮助。

解决方案 #1:

使用我自己的 collection :

{
   username: String
   comments: Array<String>
   image   : Gridfs 
}

如何使用 GridFS 获取我自己 collection 中的图像?可能吗?

解决方案 #2:

我使用 fs.files collection,其中包含元数据并添加条目用户名和评论。我试过了,还是不行。

谁可以帮助我?

谢谢

至于解决方案#1

如果您使用的是 ReactiveMongo,则有一个示例项目,具有复合服务器响应,由文件和 json

组成

https://github.com/sgodbillon/reactivemongo-demo-app/blob/master/app/controllers/Application.scala

 def showEditForm(id: String) = Action.async {
    val objectId = new BSONObjectID(id)
    // get the documents having this id (there will be 0 or 1 result)
    val futureArticle = collection.find(BSONDocument("_id" -> objectId)).one[Article]
    // ... so we get optionally the matching article, if any
    // let's use for-comprehensions to compose futures (see http://doc.akka.io/docs/akka/2.0.3/scala/futures.html#For_Comprehensions for more information)
    for {
      // get a future option of article
      maybeArticle <- futureArticle
      // if there is some article, return a future of result with the article and its attachments
      result <- maybeArticle.map { article =>
        import reactivemongo.api.gridfs.Implicits.DefaultReadFileReader
        // search for the matching attachments
        // find(...).toList returns a future list of documents (here, a future list of ReadFileEntry)
        gridFS.find(BSONDocument("article" -> article.id.get)).collect[List]().map { files =>
          val filesWithId = files.map { file =>
            file.id.asInstanceOf[BSONObjectID].stringify -> file
          }
          Ok(views.html.editArticle(Some(id), Article.form.fill(article), Some(filesWithId)))
        }
      }.getOrElse(Future(NotFound))
    } yield result
  }

您可以将其用作参考实现。

至于解决方案#2

您应该能够在 DefaultFileToSave.metadata 中存储额外的数据,然后使用 { "metadata.user" : "user"} 查询 mongo(查看 Query on MongoDB GridFS metadata (Java) )

另一个解决方案

将文件和您的元信息作为独立的实体保存,并独立管理它们,将来扩展它们会更容易。

对于 GridFS 上传功能(https://github.com/ReactiveMongo/Play-ReactiveMongo

def upload = Action(gridFSBodyParser(gridFS)) { request =>
  // here is the future file!
  val futureFile: Future[ReadFile[BSONValue]] = request.body.files.head.ref
  futureFile.map { file =>
    // do something
    Ok
  }.recover {
    case e: Throwable => InternalServerError(e.getMessage)
  }
}

以端点为例对之前进行扩展

  • /video/:id/file - 您的 GridFS 文件端点
  • /video/:id/meta - 你的元信息端点(无论你需要它是什么)
  • /video/:id(可选)- 组合文件和元响应。