SpringMVC之 文件上传和下载

1. 文件上传

1.1 前端注意事项

文件上传操作,前端的表单项需要如下三项设置:

(1)input标签的type属性应设置为file,并且注意不要在input标签中设置value属性,因为这可能导致文件上传不成功;

(2)请求方式为 method="post" ;

(3)enctype="multipart/form-data"。

1.2 后端注意事项

文件上传操作,后端需要注意:

(1)可以在项目的配置文件 application.properties或application.yml中设置文件大小限制,以避免上传过大的文件导致服务器资源耗尽,例如:

(2)后端需要写一个处理上传文件的处理器,把接收到的文件保存到服务器指定目录下等其他操作。

1.3 前后端完整示例程序

1.3.1 前端

html 复制代码
<!DOCTYPE html>
<html lang="en" xmlns="http://www.w3.org/1999/html">
<head>
    <meta charset="UTF-8">
    <title>文件上传和下载</title>
</head>
<body>
<form action="/file/upload" method="post" enctype="multipart/form-data">
    用户名:<input type="text" name="username"/><br/>
    头 像 :<input type="file" name="headerImg" /><br/>
    生活照:<input type="file" name="lifeImages" multiple></br>
    <input type="submit" value="提交"/>
</form>
</body>
</html>

1.3.2 后端

html 复制代码
package com.shg.springmvc.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.nio.file.Paths;

@Controller
public class PageTestController {
    
    @RequestMapping(value = "/file/upload", method = RequestMethod.POST)
    @ResponseBody
    public String fileUpload(@RequestParam(value = "headerImg") MultipartFile file,
                             @RequestParam(value = "lifeImages") MultipartFile[] lifeImages,
                             @RequestParam(value = "username") String userName) throws IOException {
        System.out.println("用户名:" + userName);
        System.out.println("头像 - 文件名称:" + file.getOriginalFilename());
        file.transferTo(Paths.get("D:\\tempPic\\" + file.getOriginalFilename()));

        for (MultipartFile lifeImage : lifeImages) {
            System.out.println("生活照 - 文件名称:" + lifeImage.getOriginalFilename());
            lifeImage.transferTo(Paths.get("D:\\tempPic\\" + file.getOriginalFilename()));
        }
        return "success";
    }
}

2. 文件下载

文件下载的写法比较固定,代码如下:

java 复制代码
package com.shg.springmvc.controller;

import org.springframework.core.io.InputStreamResource;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;

@RestController
public class ResponseTestController {


    /**
     * 问题一:如果文件名称中包含中文,那么浏览器会乱码
     * 问题二:如果下载的文件比较大,会oom(内存溢出)
     *
     * @return
     * @throws IOException
     */
    @RequestMapping(value = "/download", method = RequestMethod.GET)
    public ResponseEntity<InputStreamResource> response_02() throws IOException {

        // 获取要下载的文件流
        String filePath = "D:\\tempPic\\生活照3.jpg";
        File file = new File(filePath);
        FileInputStream fileInputStream = new FileInputStream(file);

        // 解决问题一:使用URLEncoder.encode()方法对文件名称进行编码
        String fileName = URLEncoder.encode("你好啊.jpg", StandardCharsets.UTF_8);

        // 解决问题二:为了避免一次性读取文件过大,导致内存溢出,可以使用 InputStreamResource 来读取文件(将文件流包装成Resource对象)
        InputStreamResource inputStreamResource = new InputStreamResource(fileInputStream);

        return ResponseEntity.ok()
                // 设置响应头,告诉浏览器如何处理
                .header(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=" + fileName)
                // 下载文件的大小
                .contentLength(file.length())
                // 内容类型:流
                .contentType(MediaType.APPLICATION_OCTET_STREAM)
                // 响应体
                .body(inputStreamResource);
    }
}
相关推荐
工业甲酰苯胺1 小时前
深入解析 Spring AI 系列:解析返回参数处理
javascript·windows·spring
小高不明2 小时前
仿 RabbitMQ 的消息队列2(实战项目)
java·数据库·spring boot·spring·rabbitmq·mvc
荆州克莱3 小时前
Golang的图形编程基础
spring boot·spring·spring cloud·css3·技术
m0_748235074 小时前
springboot中配置logback-spring.xml
spring boot·spring·logback
蒙双眼看世界4 小时前
IDEA运行Java项目总会报程序包xxx不存在
java·spring·maven
计算机学姐12 小时前
基于微信小程序的驾校预约小程序
java·vue.js·spring boot·后端·spring·微信小程序·小程序
qw94916 小时前
Spring 6 第6章——单元测试:Junit
spring·junit·单元测试
荆州克莱17 小时前
Golang的网络编程安全
spring boot·spring·spring cloud·css3·技术
清风-云烟18 小时前
使用redis-cli命令实现redis crud操作
java·linux·数据库·redis·spring·缓存·1024程序员节
好像是个likun18 小时前
spring Ioc 容器的简介和Bean之间的关系
java·后端·spring