Java下载小文件正常,大文件总是404错误

最近处理文件下载遇到奇怪的现象:小文件(30 ~ 40M)下载正常,大文件(>100M)下载总是404 

因为使用了Nginx,最初怀疑是代理配置的问题,于是

proxy_buffering off

或
proxy_buffering on;
proxy_buffers 4 4k;
proxy_busy_buffers_size 8k;
proxy_max_temp_file_size 1024m;

并
proxy_send_timeout 600;
proxy_read_timeout 600;

 结果没卵用,再细想404 是服务报出来的,于是专心改代码

 

最初代码如下

<a href='project/downloadFile?fileName=fn.docx&filePath=c:\\dir\\fn.docx' target='_self'>下载fn.docx</a> 
    @RequestMapping(value = "/downloadFile", method = RequestMethod.GET)
    @ResponseBody
    public void downloadFile(HttpServletRequest request, HttpServletResponse response) {
        try {
            String fileName = new String(
                    request.getParameter("fileName").getBytes("iso-8859-1"),
                    "UTF-8"
            );
            String filePath = new String(
                    request.getParameter("filePath").getBytes("iso-8859-1"),
                    "UTF-8"
            );

            File file = new File(filePath);
            if (!file.exists()) {
                return;
            }

            InputStream input = new FileInputStream(file);
            byte[] buffer = new byte[input.available()];
            input.read(buffer);
            input.close();

            response.reset();
            response.setHeader(
                "Content-disposition", 
                "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8")
            );
            response.setContentType("application/vnd.openxmlformats-officedocument.wordprocessingml.document");

            OutputStream output = response.getOutputStream();
            output.write(buffer);
            output.flush();
            output.close();
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
        }
    }

 

改成如下代码就好了

    @RequestMapping(value = "/downloadFile", method = RequestMethod.GET)
    @ResponseBody
    public void downloadFile(HttpServletRequest request, HttpServletResponse response) {
        BufferedInputStream input = null;
        BufferedOutputStream output = null;
        try {
            String fileName = new String(
                    request.getParameter("fileName").getBytes("iso-8859-1"),
                    "UTF-8"
            );
            String filePath = new String(
                    request.getParameter("filePath").getBytes("iso-8859-1"),
                    "UTF-8"
            );

            File file = new File(filePath);
            if (!file.exists()) {
                return;
            }

            input = new BufferedInputStream(new FileInputStream(file));

            response.setHeader(
                    "Content-disposition",
                    "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8")
            );
            response.setContentType("application/vnd.openxmlformats-officedocument.wordprocessingml.document");

            ServletOutputStream servlet = response.getOutputStream();
            output = new BufferedOutputStream(servlet);

            byte[] buffer = new byte[2048];
            int len = 0;
            while ((len = input.read(buffer, 0, buffer.length)) != -1) {
                output.write(buffer, 0, len);
            }
            output.flush();
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
        } finally {
            try {
                if (null != output) {
                    output.close();
                }
                if (null != input) {
                    input.close();
                }
            } catch (Exception e) {
                logger.error(e.getMessage(), e);
            }
        }
    }

 

我只是知其然,不知道所以然,不明白

ServletOutputStream 和 OutputStream 有啥区别?

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值