3

目前要求有一个对象 - “应用程序”,它具有以下文件:“名称”、“上传时间”和“执行文件”。

目前数据库是mongodb。我想使用文档

Class Application {
     String id;
     String name;
     String type;
     Date uploadTime;
     GridFSDBFile executeFile;
}

Dao层,我写save的时候发现不能直接关联GridFSDBfile到文档。我需要先使用 GridFsTemplate.store 保存 GridDBFile,然后使用 GridFsTemplate.findOne 按名称查找,并将对象嵌套在应用程序文档中。然后使用 MongoOperation 保存应用程序文件。

try {
        inputStream = new FileInputStream("C:/testing.app");
        gridFsOperations.store(inputStream, "test.app", "jar");

    } catch (FileNotFoundException e) {
        e.printStackTrace();
    } finally {
        if (inputStream != null) {
            try {
                inputStream.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    Query query = query(where("filename").is("test.app"));
    GridFSDBFile gridFsDBFile = gridFsOperations.findOne(query);

    Application application = new Application ();
    application.setName( "test-app");
    application.setType( "type", "Java");
    application.setexecuteFile (gridFsDBFile);

    applicationDao.save(application);

有什么方法可以调用 MongoOperation 吗?如果没有,我认为调用 GridFsTemplate.store 和 MongoOperation.save 需要在事务中执行。我记得 Mongo 不支持事务。这个怎么做?只检查 Java 代码中的事务?

4

1 回答 1

3

我发现我无法将 GridFSDBfile 直接关联到文档中。我需要先使用 GridFsTemplate.store 保存 GridDBFile,然后使用 GridFsTemplate.findOne 按名称查找,并将对象嵌套在应用程序文档中。然后使用 MongoOperation 保存应用程序文件。

你在这里弄错了。当您将文件保存在 中时GridFS,文件及其元数据的存储分布在两个集合中,即fs.filesfs.chunks。每当使用 插入GridFs API文件时,文件及其元数据都会一次性存储。

为了给你更好的画面,

执行以下指令时:

    gridFsOperations.store(inputStream, "test.app", "jar");

MongoDB制作两个条目,一个进入集合,fs.files另一个进入fs.chunks集合。

一个条目进入fs.files集合:

{
        "_id" : ObjectId("545d6699756c779b8cb8b13d"),
        "type":"jar",
        "filename" : "test.app",
        "aliases" : null,
        "chunkSize" : NumberLong(262144),
        "uploadDate" : ISODate("2014-11-08T00:40:57.298Z"),
        "length" : NumberLong(433),
        "contentType" : null,
        "md5" : "5e49ad0614687c7ad343f6f9fe6843b2"
}

该条目只有文件的元数据信息,例如文件名和类型。您甚至可以使用BasicDBObject该类设置其他元数据信息。你想包括uploadTime,

DBObject metadata = new BasicDBObject();
metadata.put("uploadTime", Calendar.getInstance().getTime());

并将其保存如下,

gridFsOperations.store(inputStream, "test.app", "jar",metadata );

它还具有一条关键信息,即在其_id字段中对包含实际文件内容的文档的引用。

另一个条目被添加到fs.chunks集合中:

{
        "_id" : ObjectId("545d6699756c779b8cb8b13e"),
        "files_id" : ObjectId("545d6699756c779b8cb8b13d"),
        "n" : 0,
        "data" : BinData(0,"PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iVVRGLTgiPz4N
Cjx4c2w6c3R5bGVzaGVldCB4bWxuczp4c2w9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkvWFNML1RyYW5z
Zm9ybSINCnZlcnNpb249IjEuMCI+DQoNCjx4c2w6b3V0cHV0IGVuY29kaW5nPSJVVEYtOCIgbWV0aG9k
PSJ4bWwiIGluZGVudD0ieWVzIi8+DQo8eHNsOnZhcmlhYmxlIG5hbWU9InRvcExldmVsIj4NCiAgICAg
ICAgPHhzbDp2YXJpYWJsZSBuYW1lPSJpbm5lciIgc2VsZWN0PSInSGknIiAvPg0KICAgICAgICA8eHNs
OnZhbHVlLW9mIHNlbGVjdD0iJGlubmVyIi8+DQo8L3hzbDp2YXJpYWJsZT4NCiAgICANCjx4c2w6dGVt
cGxhdGUgbWF0Y2g9Ii8iID4NCiAgICA8eHNsOnZhbHVlLW9mIHNlbGVjdD0iJHRvcExldmVsIiAvPg0K
PC94c2w6dGVtcGxhdGU+DQo8L3hzbDpzdHlsZXNoZWV0Pg==")
} 

这是实际文档,其中包含其Binary形式的文件内容。记下文档的files_id字段。它与从集合ObjectId中的条目中引用的相同。fs.files

这就是MongoDB维护文件内容与其元数据之间关系的方式。GridFS只是一个 API,用于将用户从处理低级实现中抽象出来。

如果不是,我认为调用 GridFsTemplate.store 和 MongoOperation.save 需要在事务中执行。我记得 Mongo 不支持事务。这个怎么做?只检查 Java 代码中的事务?

应用程序无需为此操作创建或维护任何事务。

于 2014-11-08T01:05:22.730 回答