SpringBoot+vue 实现流式下载文件

558 阅读1分钟
1、后端核心代码
public void downloadPptFile(String infoId,HttpServletResponse response) throws UnsupportedEncodingException {
        QueryWrapper<PptFile> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("ppt_info_id", infoId);
        PptFile pptFile = this.getOne(queryWrapper, false);
        //根剧网络地址获取物理地址
        String path = FileKit.getFileDir(pptFile.getFilePath().substring(1)).replace("/", File.separator);
       //====== 以上是项目业务代码=======
        // 文件下载核心代码
    	File file = new File(path);
        byte[] buffer = new byte[1024];
        BufferedInputStream bis = null;
        OutputStream os = null;
        try {
            //文件是否存在
            if (file.exists()) {
                //设置响应
                response.setCharacterEncoding("UTF-8");
                response.setHeader("content-type", "application/octet-stream");
                response.setContentType("application/octet-stream;charset=UTF-8");
                response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(pptFile.getFileName(), "utf-8"));
                os = response.getOutputStream();
                bis = new BufferedInputStream(new FileInputStream(file));
                int readLength = 0;
                while(( readLength = bis.read(buffer)) != -1){
                    //每次写入缓冲流buff读到的字节长度,而不是buff.length
                    //这个地方注意,如果直接写成了 buff.length ,下载后的文件打开时会提示内容修复
                    os.write(buffer, 0, readLength);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                if(bis != null) {
                    bis.close();
                }
                if(os != null) {
                    os.flush();
                    os.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
2、前端核心代码
// 下载PPT
      handleDown () {
        this.$http({
          method: 'get',
          url: '/ppt/file/pptFile/downloadPptFile?infoId=' + this.pptInfoForm.id,
          responseType: 'blob'
        }).then(response => {
          if (!response) {
            return
          }
          let link = document.createElement('a')
          link.href = window.URL.createObjectURL(new Blob([response.data]))
          link.target = '_blank'
          // 文件名称
          let filename = this.pptInfoForm.pptTitle + '.pptx'
          link.download = decodeURI(filename)
          document.body.appendChild(link)
          link.click()
          document.body.removeChild(link)
        }).catch(() => {

        })
      }