最近負責了一個需求:天天定時拉取第三方報表數據,生成文件,並能夠查看、下載、壓縮打包。java
遂單獨記錄下springmvc中文件的上傳、下載和壓縮打包這三個工做經常使用功能。spring
版本信息:api
<springcloud.version>Greenwich.SR2</springcloud.version> <springboot.version>2.1.7.RELEASE</springboot.version> (<spring.version>5.1.9.RELEASE</spring.version>)
//單文件上傳 @RequestMapping("/upload") @ResponseBody public BaseResult upload(@RequestParam("file") MultipartFile file) { //文件信息獲取 String fileName = file.getOriginalFilename(); long size = file.getSize()/1024; //單位 B>KB String contentType = file.getContentType(); logger.info(">> file info to upload: {}, {}KB, {}", fileName, size, contentType); //目錄生成與新文件名 String newFileName = currDateStr.substring(8, currDateStr.length()) + "_" + fileName; String dateDir = currDateStr.substring(0, 8); //20191220 File destDir = new File(upload_fspath_base, dateDir);// /xxx/upload/20191220 if(!destDir.exists()) { destDir.mkdirs(); //注意不是mkdir } //文件寫入 try { file.transferTo(new File(destDir, newFileName)); } catch (IllegalStateException | IOException e) { logger.error("保存上傳文件出錯!", e); throw new BusinessException("保存上傳文件出錯!", e); } return BaseResult.succ(); }
//多文件上傳 @RequestMapping("/uploads") @ResponseBody public BaseResult uploads(@RequestParam("files") MultipartFile[] files) { int succSize = Arrays.stream(files).map(this::upload).collect(Collectors.toList()).size(); return BaseResult.succData(succSize); }
spring.servlet.multipart.max-file-size=200MB spring.servlet.multipart.max-request-size=200MB
//文件下載 @RequestMapping("/download/{code}") public ResponseEntity<Resource> download(@PathVariable String code) { //上傳下載碼(惟一碼) //查找上傳記錄 UploadFileInfo fileInfo = uploadFileInfoRepo.findByUploadCode(code); if(Objects.nonNull(fileInfo)) { Resource resource = null; String contentType = null; try { //load file as Resource if(!RichardUtil.isStrEmpty(fileInfo.getFsPath())) { resource = new FileSystemResource(new File(fileInfo.getFsPath())); }else { resource = new UrlResource(fileInfo.getSrcPath()); } contentType = request.getServletContext().getMimeType(resource.getFile().getAbsolutePath()); } catch (IOException e) { logger.error(code, e); throw new BusinessException("資源讀取異常!", e); } if(Objects.isNull(contentType)) contentType = "application/octet-stream"; return ResponseEntity.ok() .contentType(MediaType.parseMediaType(contentType)) .header(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + fileInfo.getFileName() + "\"") .body(resource); }else { throw new BusinessException("資源未找到!"); } }
見壓縮示例一塊兒springboot
org.springframework.core.io.Resource
很好用/** * 文件(壓縮打包)下載,傳統response版 */ @RequestMapping("/manage-api/download/zip5s") @ResponseBody public void zip5s() { List<UploadFileInfo> collect5 = uploadFileInfoRepo.findAll().stream().limit(5).collect(Collectors.toList()); String showName = RichardUtil.getCurrentDatetimeStrNoFlag() + ".zip"; //java7 資源自動關閉語法糖 try(ZipOutputStream out = new ZipOutputStream(response.getOutputStream())){ response.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + showName + "\""); response.setContentType("application/octet-stream"); for(UploadFileInfo o:collect5) { //load file resource Resource resource = RichardUtil.isStrEmpty(o.getFsPath())?new UrlResource(o.getSrcPath()):new FileSystemResource(o.getFsPath()); //添加壓縮 out.putNextEntry(new ZipEntry(o.getFileName())); //寫入(方法封裝,目的流暫不關閉) RichardUtil.dump_dest_not_close(resource.getInputStream(), out); } } catch (IOException e) { logger.error(">> zip壓縮打包異常", e); throw new BusinessException(e); } }