Springmvc 下载文件

本文介绍两种在Java中实现文件下载的方法:使用HttpServletResponse和ResponseEntity。通过设置响应头和使用输出流,展示了如何从服务器下载文件,包括处理文件名编码和大文件下载的问题。
摘要由CSDN通过智能技术生成

前言

有时候项目里需要下载文件的功能,但是一时之间不知道从何下手,故此记录。

一、使用HttpServletResponse

最简单方便的便是使用HttpServletResponse,设置一下请求头,获取到输出流。

	public static void download(HttpServletRequest request, HttpServletResponse response)throws Exception {
	   
		String fileName = "要下载的文件的名字";
		String filePath = "要下载的文件在服务器的存储地址";
		
	    //设置响应头和客户端保存文件名
	    response.setCharacterEncoding("utf-8");
	    response.setContentType("multipart/form-data");
	    response.setHeader("Content-Disposition", "attachment;fileName=" + fileName);
	    
	    //打开本地文件流
        InputStream in = new FileInputStream(filePath);
        //激活下载操作
        OutputStream os = response.getOutputStream();
	    try {
	        //循环写入输出流
	        byte[] b = new byte[2048];
	        int length;
	        while ((length = in.read(b)) > 0) {
	            os.write(b, 0, length);
	        }

	    } catch (Exception e){
	        throw e;
	    } finally {
	    	os.close();
	        in.close();
		}
	    
	}

但是有时候前端拿不到文件名称,就需要把文件名称用URLEncoder编码一下。输出流和输出流的转换可以使用Hutool工具类,这样编码会更加简单。

    @GetMapping("/doc")
    public void downloadStatisticsDoc(HttpServletResponse response) throws Exception {

        //response设置
        String today = DateUtil.today();
        String fileName = "txt文件名称" + today + ".txt";
        response.setCharacterEncoding(StandardCharsets.UTF_8.name());
        response.setContentType(MediaType.TEXT_PLAIN_VALUE);
        response.setHeader("Content-Disposition", "attachment;fileName=" + URLEncoder.encode(fileName, StandardCharsets.UTF_8.name()));

        //文档内容
        String statistics = "要下载的文本内容";
        try(BufferedInputStream in = new BufferedInputStream(new ByteArrayInputStream(statistics.getBytes()));
            BufferedOutputStream out = new BufferedOutputStream(response.getOutputStream())
        ){
            IoUtil.copy(in, out);
        }
    }

二、使用ResponseEntity

使用方法基本一样,就是稍微简介了一些,也可以下载byte数组。

    public ResponseEntity<Object> download(HttpServletRequest request)throws Exception{
        
        byte[] data = "获取到的byte数组,也可以是输入流读取来的";
        String fileName = "文件名字";
        
        //设置响应头
        HttpHeaders headers = new HttpHeaders();
        headers.setCacheControl("no-cache, no-store, must-revalidate");
        //防止中文乱码
        headers.setContentDispositionFormData("attachment",new String(fileName.getBytes("UTF-8"), "iso-8859-1"));
        headers.setContentType(MediaType.APPLICATION_OCTET_STREAM);
        //headers.setContentLength(file.getContentLength());
        headers.setPragma("no-cache");
        
        return new ResponseEntity<Object>(data, headers, HttpStatus.CREATED);
    }

写在最后的话

这两种下载方式各有优缺点吧,ResponseEntity比较简洁一些,但是是一种一次性读取的下载方式,下载太大文件会导致内存溢出。使用response对下载的文件大小无限制(循环读取一定量的字节写入到输出流中,因此不会造成内存溢出,但是在下载人数过多的时候应该还是出现一些异常)。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值