spring boot集成MongoDb存储文档

1、下载MongoDb
https://www.mongodb.com/try/download/community
安装很简单、基本都是下一步。安装好需要进行环境变量的配置、在path里面吧对应的bin路径加入到里面D:\mongodb-win32-x86_64-2012plus-4.2.23\bin
2、集成
配置YML

spring:
  data:
    mongodb:
      host: localhost
      port: 27017
      database: test

加入依赖

<dependency>
    <groupId>org.springframework.bootgroupId>
    <artifactId>spring-boot-starter-data-mongodbartifactId>
dependency>

新建FileDocument实体类

import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.experimental.Accessors;
import org.springframework.data.mongodb.core.mapping.Document;

import java.io.Serializable;
import java.util.Date;

@Document
@Data
@EqualsAndHashCode(callSuper = false)
@Accessors(chain = true)
public class FileDocument implements Serializable {
    /**
     * id
     */
    private String id;
    /**
     * 文件名称
     */
    private String name;
    /**
     * 文件大小
     */
    private long size;
    /**
     * 上传时间
     */
    private Date uploadDate;
    /**
     * 文件的md5值
     */
    private String md5;
    /**
     * 文件内容
     */
    private byte[] content;
    /**
     * 文件类型
     */
    private String contentType;
    /**
     * 文件后缀
     */
    private String suffix;
    /**
     * 文件描述
     */
    private String description;
    /**
     * 大文件管理GridFS的ID
     */
    private String gridfsId;
}

新建FileService、FileServiceImpl服务类实现类

import com.mongodb.client.gridfs.GridFSBucket;
import com.mongodb.client.gridfs.GridFSDownloadStream;
import com.mongodb.client.gridfs.model.GridFSFile;
import com.mongodb.client.result.DeleteResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Field;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.gridfs.GridFsResource;
import org.springframework.data.mongodb.gridfs.GridFsTemplate;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Date;
import java.util.List;
import java.util.Optional;
import java.util.UUID;
@Service
public class FileServiceImpl_1 implements FileService_1 {
    private static String collectionName = "fileDate";
    @Autowired
    private  MongoTemplate mongoTemplate;
    @Autowired
    private  GridFsTemplate gridFsTemplate;
    @Autowired
    private  GridFSBucket gridFSBucket;

    /**
     * 表单上传附件
     *
     * @param md5
     * @param file
     * @return
     */
    @Override
    public FileDocument saveFile(String md5, MultipartFile file) {
        //已存在该文件,则实现秒传
        FileDocument fileDocument = getByMd5(md5);
        if (fileDocument != null) {
            return fileDocument;
        }

        fileDocument = new FileDocument();
        fileDocument.setName(file.getOriginalFilename());
        fileDocument.setSize(file.getSize());
        fileDocument.setContentType(file.getContentType());
        fileDocument.setUploadDate(new Date());
        fileDocument.setMd5(md5);
        String suffix = file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf("."));
        fileDocument.setSuffix(suffix);

        try {
            //文件存入gridfs
            String gridfsId = uploadFileToGridFS(file.getInputStream(), file.getContentType());
            fileDocument.setGridfsId(gridfsId);
            //fileDocument.setContent();
            //上传的信息保存在mongodb
            fileDocument = mongoTemplate.save(fileDocument, collectionName);
        } catch (IOException ex) {
            ex.printStackTrace();
        }
        return fileDocument;
    }

    /**
     * 上传文件到Mongodb的GridFs中
     *
     * @param in
     * @param contentType
     * @return
     */
    private String uploadFileToGridFS(InputStream in, String contentType) {
        String gridfsId = UUID.randomUUID().toString();
        //文件,存储在GridFS中
        gridFsTemplate.store(in, gridfsId, contentType);
        return gridfsId;
    }

    /**
     * 删除附件
     *
     * @param id           文件id
     * @param isDeleteFile 是否删除文件
     */
    @Override
    public void removeFile(String id, boolean isDeleteFile) {
        FileDocument fileDocument = mongoTemplate.findById(id, FileDocument.class, collectionName);
        if (fileDocument != null) {
            Query query = new Query().addCriteria(Criteria.where("_id").is(id));
            DeleteResult result = mongoTemplate.remove(query, collectionName);
            System.out.println("result:" + result.getDeletedCount());

            if (isDeleteFile) {
                Query deleteQuery = new Query().addCriteria(Criteria.where("filename").is(fileDocument.getGridfsId()));
                gridFsTemplate.delete(deleteQuery);
            }
        }
    }

    /**
     * 查询附件
     *
     * @param id 文件id
     * @return
     * @throws IOException
     */
    @Override
    public Optional<FileDocument> getById(String id) {
        FileDocument fileDocument = mongoTemplate.findById(id, FileDocument.class, collectionName);
        if (fileDocument != null) {
            Query gridQuery = new Query().addCriteria(Criteria.where("filename").is(fileDocument.getGridfsId()));
            try {
                GridFSFile fsFile = gridFsTemplate.findOne(gridQuery);
                GridFSDownloadStream in = gridFSBucket.openDownloadStream(fsFile.getObjectId());
                if (in.getGridFSFile().getLength() > 0) {
                    GridFsResource resource = new GridFsResource(fsFile, in);
                    fileDocument.setContent(inputStreamToByte(resource.getInputStream()));
                    return Optional.of(fileDocument);
                } else {
                    fileDocument = null;
                    return Optional.empty();
                }
            } catch (IOException ex) {
                ex.printStackTrace();
            }
        }
        return Optional.empty();
    }

    /**
     * 流转换成byte数组
     *
     * @param inStream
     * @return
     * @throws IOException
     */
    private byte[] inputStreamToByte(InputStream inStream) throws IOException {
        ByteArrayOutputStream swapStream = new ByteArrayOutputStream();
        //buff用于存放循环读取的临时数据
        byte[] buff = new byte[100];
        int rc = 0;
        while ((rc = inStream.read(buff, 0, 100)) > 0) {
            swapStream.write(buff, 0, rc);
        }
        return swapStream.toByteArray();
    }


    /**
     * 根据md5获取文件对象
     *
     * @param md5
     * @return
     */
    @Override
    public FileDocument getByMd5(String md5) {
        Query query = new Query().addCriteria(Criteria.where("md5").is(md5));
        return mongoTemplate.findOne(query, FileDocument.class, collectionName);
    }

    /**
     * 文件分页
     *
     * @param pageIndex
     * @param pageSize
     * @return
     */
    @Override
    public List<FileDocument> listFilesByPage(int pageIndex, int pageSize) {
        Sort sort = Sort.by(Sort.Order.desc("uploadDate"));
        Query query = new Query().with(sort);
        long skip = (pageIndex - 1) * pageSize;
        query.skip(skip);
        query.limit(pageSize);
        Field field = query.fields();
        field.exclude("content");
        List<FileDocument> files = mongoTemplate.find(query, FileDocument.class, collectionName);
        return files;
    }
}
import org.springframework.web.multipart.MultipartFile;

import java.util.List;
import java.util.Optional;

public interface FileService_1 {
    /**
     * 保存信息的文件
     *
     * @param md5
     * @param file
     * @return
     */
    public FileDocument saveFile(String md5, MultipartFile file);

    /**
     * 移除文件
     *
     * @param id
     * @param isDeleteFile
     */
    public void removeFile(String id, boolean isDeleteFile);

    /**
     * 根据id查询附件
     *
     * @param id
     * @return
     */
    public Optional<FileDocument> getById(String id);

    /**
     * 根据md5获取文件对象
     *
     * @param md5
     * @return
     */
    public FileDocument getByMd5(String md5);

    /**
     * 文件分页
     *
     * @param pageIndex
     * @param pageSize
     * @return
     */
    public List<FileDocument> listFilesByPage(int pageIndex, int pageSize);
}

在这里需要注意了@Autowired
private GridFSBucket gridFSBucket;这个导入的时候可能报错、这时候我们需要做初始化配置。增加MongoConfig类

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 gridFSBucket = GridFSBuckets.create(database);
        return gridFSBucket ;
    }
}

Controller类

/**
     * 上传文件列表
     *
     * @param pageIndex
     * @param pageSize
     * @return
     */
    @RequestMapping("/list")
    public List<FileDocument> list(int pageIndex, int pageSize) {
        return fileService_1.listFilesByPage(pageIndex, pageSize);
    }

    /**
     * 查询返回值\在线打开
     *
     * @param id 文件id
     * @return
     */
    @GetMapping("/viewFile")
    public ResponseEntity<Object> serveFileOnlines(String id) {
        Optional<FileDocument> file = fileService_1.getById(id);
        if (file.isPresent()) {
            return ResponseEntity.ok()
                    .header(HttpHeaders.CONTENT_DISPOSITION, "fileName=" + file.get().getName())
                    .header(HttpHeaders.CONTENT_TYPE, file.get().getContentType())
                    .header(HttpHeaders.CONTENT_LENGTH, file.get().getSize() + "").header("Connection", "close")
                    .body(file.get().getContent());
        } else {
            return ResponseEntity.status(HttpStatus.NOT_FOUND).body("File was not found");
        }
    }

    /**
     * 下载文件
     *
     * @param id
     * @return
     * @throws UnsupportedEncodingException
     */
    @GetMapping("/down")
    public ResponseEntity<Object> downloadFileById(String id) throws UnsupportedEncodingException {
        Optional<FileDocument> file = fileService_1.getById(id);
        if (file.isPresent()) {
            return ResponseEntity.ok()
                    .header(HttpHeaders.CONTENT_DISPOSITION, "attachment; fileName=" + URLEncoder.encode(file.get().getName(), "utf-8"))
                    .header(HttpHeaders.CONTENT_TYPE, "application/octet-stream")
                    .header(HttpHeaders.CONTENT_LENGTH, file.get().getSize() + "").header("Connection", "close")
                    .body(file.get().getContent());
        } else {
            return ResponseEntity.status(HttpStatus.NOT_FOUND).body("File was not found");
        }
    }

    /**
     * 表单上传文件
     * 当数据库中存在该md5值时,可以实现秒传功能
     *
     * @param file 文件
     * @return
     */
    @PostMapping("/upload")
    public JSONObject formUpload(@RequestParam("file") MultipartFile file) {
        JSONObject json = new JSONObject();
        try {
            if (file != null && !file.isEmpty()) {
                String fileMd5 = getMD5(file.getInputStream());
                FileDocument fileDocument = fileService_1.saveFile(fileMd5, file);

                System.out.println(fileDocument);
                json.put("code","1");
                json.put("msg","上传成功");
                json.put("date",fileDocument.getId());
            } else {
                json.put("code","0");
                json.put("msg","请上传文件");
                json.put("date","");
            }
        } catch (IOException e) {
            json.put("code","-1");
            json.put("msg","上传失败");
            json.put("date","");
        } catch (Exception e) {
            json.put("code","-1");
            json.put("msg","上传失败");
            json.put("date","");

        }
        return json;
    }

    /**
     * 删除附件
     *
     * @param id
     * @return
     */
    @GetMapping("/delete")
    public JSONObject deleteFileByGetMethod(String id) {
        JSONObject json = new JSONObject();
        if (id != null) {
            fileService_1.removeFile(id, true);
            json.put("code",1);
            json.put("msg","删除成功");
            json.put("date","");
        } else {
            json.put("code",0);
            json.put("msg","删除失败");
            json.put("date","");
        }
        return json;
    }

    /**
     * 流转换成MD5字符串
     *
     * @param inputStream
     * @return
     */
    private String getMD5(InputStream inputStream) {
        BigInteger md5 = null;
        try {
            byte[] buffer = inputStreamToByte(inputStream);
            MessageDigest md = MessageDigest.getInstance("MD5");
            md.update(buffer, 0, buffer.length);
            byte[] b = md.digest();
            md5 = new BigInteger(1, b);
        } catch (NoSuchAlgorithmException | IOException e) {
            e.printStackTrace();
        }
        assert md5 != null;
        return md5.toString(16);
    }

    /**
     * 流转换成byte数组
     *
     * @param inStream
     * @return
     * @throws IOException
     */
    private byte[] inputStreamToByte(InputStream inStream) throws IOException {
        ByteArrayOutputStream swapStream = new ByteArrayOutputStream();
        //buff用于存放循环读取的临时数据
        byte[] buff = new byte[100];
        int rc = 0;
        while ((rc = inStream.read(buff, 0, 100)) > 0) {
            swapStream.write(buff, 0, rc);
        }
        return swapStream.toByteArray();
    }

数据库显示
spring boot集成MongoDb存储文档_第1张图片
spring boot集成MongoDb存储文档_第2张图片
spring boot集成MongoDb存储文档_第3张图片

你可能感兴趣的:(Java,mongodb,spring,boot,数据库)