我们经常会遇到这样的场景:上传/下载文件。
有两种思路可以解决这个问题:
(1)将文件存储在服务器的文件系统中;
(2)将文件存储在数据库中。
如果我们选择(2),那么我们可以使用MongoDB GridFS 用于存储大小超过 16MB 的文件(文档,压缩文件,音视频,软件)。
一、MongoDB GridFS 介绍
MongoDB GridFS 是一个分布式文件系统,可用于存储/检索大小超过 16MB 的文件。
内部实现:将文件分割为一个个 chunk (默认大小为 255KB)进行存储。
两个优点:
(1)可以存储大文件(超过 16MB);
(2)可以从文件的中间位置访问文件。
二、代码示例
1 public class FileService {
2
3 // 返回DB
4 private DB getDB() {
5 // ...
6 }
7
8 /* 根据getDB()返回的DB新建一个GridFS实例并返回
9 * 这个GridFS实例用于上传、下载、删除、查找文件。
10 */
11 private GridFS getGridFS() {
12 return new GridFS(getDB(), "自己定义的collection名");
13 }
14
15 /**
16 * 保存类型为MultipartFile的文件
17 *
18 * @param multipartFile
19 * @throws IOException
20 */
21 public void saveOne(final MultipartFile multipartFile) throws IOException {
22 saveOne(multipartFile.getInputStream(), multipartFile.getOriginalFilename());
23
24 }
25
26 /**
27 * 保存类型为java.io.File的文件
28 *
29 * @param file
30 * @throws IOException
31 */
32 public void saveOne(final File file) throws IOException {
33 saveOne(new FileInputStream(file), file.getName());
34 }
35
36 public void saveOne(final InputStream in, final String fileName) {
37 GridFSInputFile gridFSInputFile = getGridFS().createFile(in);
38 gridFSInputFile.setFilename(fileName);
39 gridFSInputFile.save();
40
41 }
42
43 /**
44 * 查询所有已上传的文件
45 *
46 * @return
47 */
48 public Object queryAllFile() {
49 List<GridFSDBFile> result = getGridFS().find((DBObject) null);
50 List<Map<String, Object>> finalResult = new ArrayList<>();
51 Map<String, Object> map = null;
52 for (GridFSDBFile file : result) {
53 map = new HashMap<>();
54 map.put("id", ((ObjectId) file.getId()).toHexString());
55 map.put("fileName", file.getFilename());
56 map.put("length", file.getLength());
57 finalResult.add(map);
58
59 }
60 return finalResult;
61 }
62
63 /**
64 * 查询指定id的文件
65 *
66 * @param hexStringId
67 * 十六进制的id
68 * @return
69 */
70 public GridFSDBFile queryOne(final String hexStringId) {
71 GridFSDBFile file = getGridFS().findOne(new ObjectId(hexStringId));
72 return file;
73
74 }
75
76 /**
77 * 删除给定id的文件
78 *
79 * @param hexStringId
80 */
81 public void removeOne(final String hexStringId) {
82 getGridFS().remove(new ObjectId(hexStringId));
83 }
84 }
代码比较简单,就不做过多说明了。