SpringBoot 2.x (3):文件上传

匿名 (未验证) 提交于 2019-12-02 21:35:18

文件上传有两个要点

一是如何高效地上传:使用MultipartFile替代FileOutputSteam

二是上传文件的路径问题的解决:使用路径映射

文件路径通常不在classpath,而是本地的一个固定路径或者是一个文件服务器路径

SpringBoot的路径:

src/main/java:存放代码

src/main/resources:存放资源

  static: 存放静态文件:css、js、image (访问方式 http://localhost:8080/js/main.js)

  templates:存放静态页面:html,jsp

  application.properties:配置文件

但是要注意:

比如我在static下新建index.html,那么就可以访问localhost:8080/index.html看到页面

如果在templates下新建index.html,那么访问会显示错误,除非在Controller中进行跳转

如果想对默认静态资源路径进行修改,则在application.properties中配置:

spring.resources.static-locations = classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/ 

这里默认的顺序是先从/META-INF/resources中进行寻找,最后找到/public,可以在后边自行添加

文件上传不是老问题,这里就当是巩固学习了

方式:MultipartFile file,源自SpringMVC

首先需要一个文件上传的页面

在static目录下新建一个html页面:

<!DOCTYPE html> <html> <head> <title>文件上传</title> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> </head> <body>     <form enctype="multipart/form-data" method="post" action="/upload">         文件:<input type="file" name="head_img" /> 姓名:<input type="text"             name="name" /> <input type="submit" value="上传" />     </form> </body> </html>

文件上传成功否需要返回的应该是一个封装的对象:

package org.dreamtech.springboot.domain;  import java.io.Serializable;  public class FileData implements Serializable {     private static final long serialVersionUID = 8573440386723294606L;     // 返回状态码:0失败、1成功     private int code;     // 返回数据     private Object data;     // 错误信息     private String errMsg;      public int getCode() {         return code;     }      public void setCode(int code) {         this.code = code;     }      public Object getData() {         return data;     }      public void setData(Object data) {         this.data = data;     }      public String getErrMsg() {         return errMsg;     }      public void setErrMsg(String errMsg) {         this.errMsg = errMsg;     }      public FileData(int code, Object data) {         super();         this.code = code;         this.data = data;     }      public FileData(int code, Object data, String errMsg) {         super();         this.code = code;         this.data = data;         this.errMsg = errMsg;     }  }

处理文件上传的Controller:

package org.dreamtech.springboot.controller;  import java.io.File; import java.util.UUID;  import javax.servlet.http.HttpServletRequest;  import org.dreamtech.springboot.domain.FileData; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.RestController; import org.springframework.web.multipart.MultipartFile;  @RestController public class FileController {     private static final String FILE_PATH = "D:\\temp\\images\\";     static {         File file = new File(FILE_PATH);         if (!file.exists()) {             file.mkdirs();         }     }      @RequestMapping("/upload")     private FileData upload(@RequestParam("head_img") MultipartFile file, HttpServletRequest request) {         if (file.isEmpty()) {             return new FileData(0, null, "文件不能为空");         }         String name = request.getParameter("name");         System.out.println("用户名:" + name);         String fileName = file.getOriginalFilename();         System.out.println("文件名:" + fileName);         String suffixName = fileName.substring(fileName.lastIndexOf("."));         System.out.println("后缀名:" + suffixName);         fileName = UUID.randomUUID() + suffixName;         String path = FILE_PATH + fileName;         File dest = new File(path);         System.out.println("文件路径:" + path);         try {             // transferTo文件保存方法效率很高             file.transferTo(dest);             System.out.println("文件上传成功");             return new FileData(1, fileName);         } catch (Exception e) {             e.printStackTrace();             return new FileData(0, fileName, e.toString());         }     } }

还有问题要处理,保存图片的路径不是项目路径,而是本地的一个固定路径,那么要如何通过URL访问到图片呢?

对路径进行映射:比如我图片保存在D:\temp\image,那么我们希望访问localhost:8080/image/xxx.png得到图片

可以修改Tomcat的配置文件,也可以按照下面的配置:

package org.dreamtech.springboot.config;  import org.springframework.context.annotation.Configuration; import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;  @Configuration public class MyWebAppConfigurer implements WebMvcConfigurer {     @Override     public void addResourceHandlers(ResourceHandlerRegistry registry) {         registry.addResourceHandler("/image/**").addResourceLocations("file:D:/temp/images/");     } }

还有一些细节问题不得忽略:对文件大小进行限制

package org.dreamtech.springboot.config;  import javax.servlet.MultipartConfigElement;  import org.springframework.boot.web.servlet.MultipartConfigFactory; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.util.unit.DataSize;  @Configuration public class FileSizeConfigurer {     @Bean     public MultipartConfigElement multipartConfigElement() {         MultipartConfigFactory factory = new MultipartConfigFactory();         // 单个文件最大10MB         factory.setMaxFileSize(DataSize.ofMegabytes(10L));         /// 设置总上传数据总大小10GB         factory.setMaxRequestSize(DataSize.ofGigabytes(10L));         return factory.createMultipartConfig();     } }

打包后的项目如何处理文件上传呢?

顺便记录SpringBoot打包的坑,mvn clean package运行没有问题,但是不太方便

于是eclipse中run as maven install,但是会报错,根本原因是没有配置JDK,配置的是JRE:

解决:https://blog.csdn.net/lslk9898/article/details/73836745

图片量不大的时候,我们可以用自己的服务器自行处理,

如果图片量很多,可以采用图片服务器,自己用Nginx搭建或者阿里OSS等等

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!