文件下载方式

1.文件普通下载:

    /**
     * 文件下载
     *
     * @param response HttpServletResponse
     * @param path     文件地址
     */
    public static final void downloadFile(
           String path,HttpServletRequest request, HttpServletResponse response) 
    {
        //获取path文件路径最后斜线的下表索引,并判断path文件路径以"/"还是"\\"分隔的
        int index=path.lastIndexOf("/");
        if(index==-1){
            index=path.lastIndexOf("\\");
        }
        //获取下载文件名
        String fileName=path.substring(index+1);
        File file = new File(path);
        //判断存在
        if (!file.exists()) {
            logger.error("文件不存在");
            return;
        }
        // 以流的形式下载文件
        try (
                //文件输入流对象
                FileInputStream fileInputStream = new FileInputStream(file);
                InputStream inputStream = new BufferedInputStream(fileInputStream);
                //文件输出流对象
                OutputStream outputStream = new 
                                  BufferedOutputStream(response.getOutputStream());
            )
        {

            byte[] buffer = new byte[inputStream.available()];
            while (inputStream.read(buffer) > 0) {

            }

            response.reset();  // 清空response
            // 设置response的Header
            response.setCharacterEncoding(StandardCharsets.UTF_8.name());

            String agent = request.getHeader("User-Agent").toLowerCase();
            //针对IE或者以IE为内核的浏览器:
            if (agent.indexOf("msie") >= 0 || agent.indexOf("trident") >= 0) {
                fileName = URLEncoder.encode(fileName, StandardCharsets.UTF_8.name());
            } else {
                //非IE浏览器的处理:
                fileName = new String(fileName.getBytes(StandardCharsets.UTF_8.name()), 
                                                   StandardCharsets.ISO_8859_1.name());
            }

            //设置下载方式
            response.addHeader("Content-Disposition", "attachment;filename=" + fileName);
            //告诉浏览器(客户端)下载文件类型
            response.setContentType("audio/wav");
            response.addHeader("Content-Length", Long.toString(file.length()));
            response.setHeader("Access-Control-Allow-Origin", "*");
            //将文件流写出到响应输出流中
            outputStream.write(buffer);
            outputStream.flush();
        } catch (IOException e) {
            logger.error("名为:{}的文件下载出错,保存信息:", fileName, e);
        }
    }

2.文件压缩下载:

    /**
     * 判断下载文件的浏览器,对不同浏览器进行下载文件中文名称乱码处理
     * @param zipFileName  压缩文件名 如:1.zip
     * @param request      请求对象
     */
    public static final String setBrowser(
           String zipFileName, HttpServletRequest request
         ) throws UnsupportedEncodingException 
    {
        //从请求头获取User-Agent属性值
        String agent = request.getHeader("User-Agent").toLowerCase();
        //针对IE或者以IE为内核的浏览器:
        if (agent.indexOf("msie") >= 0 || agent.indexOf("trident") >= 0) {
            zipFileName = URLEncoder.encode(zipFileName, StandardCharsets.UTF_8.name());
        } else {
            //非IE浏览器的处理:
            zipFileName = new String(zipFileName.getBytes(StandardCharsets.UTF_8.name()), 
                                                     StandardCharsets.ISO_8859_1.name());
        }
        return zipFileName;
    }

    /**
     * 设置下载请求头参数
     * @param zipFileName  压缩文件名 如:1.zip
     * @param request      请求对象
     * @param response     响应对象
     */
    public static final void setResponseHeader(
           String zipFileName,HttpServletRequest request, 
           HttpServletResponse response
         ) throws UnsupportedEncodingException 
    {
        response.reset();  // 清空response
        // 设置response的Header
        response.setCharacterEncoding(StandardCharsets.UTF_8.name());
        //告诉浏览器(客户端)下载文件类型
        response.setContentType("application/octet-stream"); 
        zipFileName = setBrowser(zipFileName,request);
        //设置以什么方式下载,attachment:附件方式下载,inline:页面打开
        response.addHeader("Content-Disposition", "attachment;filename=" + zipFileName);
    }

    /**
     * 压缩下载文件
     * @param zipFileName  压缩文件名 如:1.zip
     * @param list         下载文件地址集合
     * @param request      请求对象
     * @param response     响应对象
     * @throws UnsupportedEncodingException
     */
    public static final void zipDownload(
           String zipFileName, List<String> list, 
           HttpServletRequest request, HttpServletResponse response
         ) throws UnsupportedEncodingException 
    {
        //设置下载请求头参数
        setResponseHeader(zipFileName,request,response);
        //设置压缩流:直接写入response,实现边压缩边下载
        AtomicLong atomicLong = new AtomicLong();
        try (
                //使用缓存输出流对象,获取响应输出流,加快输出流效率,提高下载速度
                BufferedOutputStream bos = new 
                               BufferedOutputStream(response.getOutputStream());
                ZipOutputStream zos = new ZipOutputStream(bos);   //压缩输出流对象
                DataOutputStream dos = new DataOutputStream(zos); //数据输出流对象
        )
        {
            zos.setMethod(ZipOutputStream.DEFLATED); //设置压缩方法
            if (!CollectionUtils.isEmpty(list)) { //判断list对象集合是否为空
                list.stream().forEach(path -> {
                    //获取path文件路径最后分隔的斜线下标索引
                    int index = path.lastIndexOf("/");
                    if (index == -1) { //判断path文件路径是"/"还是"\\"分隔的
                        index = path.lastIndexOf("\\");
                    }
                    //根据path文件路径,获取要下载的文件名
                    String fileName = path.substring(index + 1);
                    File file = new File(path); //获取path文件路径下的文件对象
                    atomicLong.addAndGet(file.length()); //保存每次下载文件长度
                    if (file.exists()) {
                        try ( //文件输入流对象
                              FileInputStream inputStream = new FileInputStream(file);
                            ) 
                          {
                            //向压缩输出流对象中添加zip实体(一个文件对应一个ZipEntry)
                            zos.putNextEntry(new ZipEntry(fileName));
                            byte[] bytes = new byte[1024];
                            int length = 0;
                            //将文件流循环写入压缩输出流中
                            while ((length = inputStream.read(bytes)) != -1) {
                                dos.write(bytes, 0, length);
                            }
                          } catch (IOException e) {
                            logger.error("名为:{}的文件下载出错,保存信息:", fileName, e);
                          }
                    }
                });

            }
            //
            response.addHeader("Content-Length", Long.toString(atomicLong.get()));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值