GridFS文件操作
目录
1. GridFS介绍
GridFS
是MongoDB
提供的用于持久化存储文件的模块,CMS
使用MongoDB
存储数据,使用GridFS
可以快速集成
开发。
它的工作原理是:
在GridFS
存储文件是将文件分块存储,文件会按照256KB的大小分割成多个块进行存储,GridFS
使用两个集合
(collection
)存储文件,一个集合是chunks
, 用于存储文件的二进制数据;一个集合是files
,用于存储文件的元数据信息(文件名称、块大小、上传时间等信息)。
从GridFS
中读取文件要对文件的各各块进行组装、合并。
详细参考:https://docs.mongodb.com/manual/core/gridfs/
2. GridFS 存取文件测试
2.1 新建项目配置pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.2.2.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.example</groupId>
<artifactId>demo-monogo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>demo-monogo</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-mongodb</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
2.2 在application.yml
配置mongodb
spring:
data:
mongodb:
uri: mongodb://root:root@localhost:27017
database: xc_cms
2.3 GridFS
存取文件测试
1、存文件
使用GridFsTemplate
存储文件测试代码:
向测试程序注入GridFsTemplate
。
package com.example.demomonogo;
import org.bson.types.ObjectId;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.mongodb.gridfs.GridFsTemplate;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
@SpringBootTest
class DemoMonogoApplicationTests {
@Autowired
GridFsTemplate gridFsTemplate;
@Test
public void testGridFs() throws FileNotFoundException {
//要存储的文件
File file = new File("D:\\test\\user_selected.png");
//定义输入流
FileInputStream inputStram = new FileInputStream(file);
//向GridFS存储文件
ObjectId objectId = gridFsTemplate.store(inputStram, "user_selected.png", "image/png");
//得到文件ID
String fileId = objectId.toString();
System.out.println(fileId);
}
}
文件以及成功被存入到GridFS
2.4 读取文件
1)在config
包中定义Mongodb
的配置类,如下:
GridFSBucket
用于打开下载流对象
package com.example.demomonogo.config;
/**
* @author john
* @date 2019/12/21 - 10:39
*/
import com.mongodb.MongoClient;
import com.mongodb.client.MongoDatabase;
import com.mongodb.client.gridfs.GridFSBucket;
import com.mongodb.client.gridfs.GridFSBuckets;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class MongoConfig {
@Value("${spring.data.mongodb.database}")
String db;
@Bean
public GridFSBucket getGridFSBucket(MongoClient mongoClient) {
MongoDatabase database = mongoClient.getDatabase(db);
GridFSBucket bucket = GridFSBuckets.create(database);
return bucket;
}
}
2)测试代码如下
package com.example.demomonogo;
import com.mongodb.client.gridfs.GridFSBucket;
import com.mongodb.client.gridfs.GridFSDownloadStream;
import com.mongodb.client.gridfs.model.GridFSFile;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.gridfs.GridFsResource;
import org.springframework.data.mongodb.gridfs.GridFsTemplate;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
@SpringBootTest
class DemoMonogoApplicationTests {
@Autowired
GridFsTemplate gridFsTemplate;
@Autowired
GridFSBucket gridFSBucket;
@Test
public void queryFile() throws IOException {
String fileId = "5dfd851306322e6b12057a40";
//根据id查询文件
GridFSFile gridFSFile =
gridFsTemplate.findOne(Query.query(Criteria.where("_id").is(fileId)));
//打开下载流对象
GridFSDownloadStream gridFSDownloadStream =
gridFSBucket.openDownloadStream(gridFSFile.getObjectId());
//创建gridFsResource,用于获取流对象
GridFsResource gridFsResource = new GridFsResource(gridFSFile, gridFSDownloadStream);
//获取流中的数据
InputStream inputStream = gridFsResource.getInputStream();
File f1 = new File("D:\\test\\get.png");
if (!f1.exists()) {
f1.getParentFile().mkdirs();
}
byte[] bytes = new byte[1024];
// 创建基于文件的输出流
FileOutputStream fos = new FileOutputStream(f1);
int len = 0;
while ((len = inputStream.read(bytes)) != -1) {
fos.write(bytes, 0, len);
}
inputStream.close();
fos.close();
}
}
2.5 删除文件
package com.example.demomonogo;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.gridfs.GridFsTemplate;
import java.io.IOException;
@SpringBootTest
class DemoMonogoApplicationTests {
@Autowired
GridFsTemplate gridFsTemplate;
//删除文件
@Test
public void testDelFile() throws IOException {
//根据文件id删除fs.files和fs.chunks中的记录
gridFsTemplate.delete(Query.query(Criteria.where("_id").is("5dfd851306322e6b12057a40")));
}
}