原文: https://howtodoinjava.com/spring-mvc/spring-mvc-multi-file-upload-example/
Spring MVC 为任何应用程序中的多文件上传功能提供了开箱即用的支持。 本教程使用CommonsMultipartResolver
,并且需要 apache commons 文件上载和 apache commons io 依赖项。
pom.xml
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.3.1</version>
</dependency>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.6</version>
</dependency>
1. Spring MVC MultipartFile
接口
上传到 Spring MVC 应用程序的文件将包装在MultipartFile
对象中。 我们需要做的就是编写一个属性类型为MultipartFile
的域类。 该界面具有获取上传文件的名称和内容的方法,例如 getBytes()
,getInputStream()
,getOriginalFilename()
, getSize()
,isEmpty()
和tranferTo()
。
例如,要将上传的文件保存到文件系统,我们可以使用transferTo
方法:
文件上传到文件系统
File file = new File(...);
multipartFile.transferTo(file);
2. 用于文件上传的域类
您需要创建一个具有必要属性的简单域类,并创建一个用于存储List<MultipartFile>
类型的文件的域类。
为了构建此示例,我编写了此域类。
Product.java
public class Product implements Serializable
{
private static final long serialVersionUID = 74458L;
@NotNull
@Size(min=1, max=10)
private String name;
private String description;
private List<MultipartFile> images;
//getters and setters
}
3. Spring MVC 多文件上传控制器
在控制器类中,我们将在域类中获取上载文件的预填充详细信息。 只需获取详细信息,然后根据应用程序设计将文件存储在文件系统或数据库中即可。
DemoProductController.java
@Controller
public class DemoProductController
{
@RequestMapping("/save-product")
public String uploadResources( HttpServletRequest servletRequest,
@ModelAttribute Product product,
Model model)
{
//Get the uploaded files and store them
List<MultipartFile> files = product.getImages();
List<String> fileNames = new ArrayList<String>();
if (null != files && files.size() > 0)
{
for (MultipartFile multipartFile : files) {
String fileName = multipartFile.getOriginalFilename();
fileNames.add(fileName);
File imageFile = new File(servletRequest.getServletContext().getRealPath("/image"), fileName);
try
{
multipartFile.transferTo(imageFile);
} catch (IOException e)
{
e.printStackTrace();
}
}
}
// Here, you can save the product details in database
model.addAttribute("product", product);
return "viewProductDetail";
}
@RequestMapping(value = "/product-input-form")
public String inputProduct(Model model) {
model.addAttribute("product", new Product());
return "productForm";
}
}
4. Spring MVC 配置更改
为了支持多部分请求,我们需要在配置文件中声明multipartResolver
bean。
beans.xml
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="20848820" />
</bean>
等效的 Java 注解配置为:
@Bean(name = "multipartResolver")
public CommonsMultipartResolver multipartResolver()
{
CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver();
multipartResolver.setMaxUploadSize(20848820);
return multipartResolver;
}
此外,我们可能希望将服务器上的文件存储路径映射为资源。 这将是 spring mvc 文件上传目录。
<mvc:resources mapping="/image/**" location="/image/" />
本示例使用的完整配置文件为:
beans.xml
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/context/
http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">
<context:component-scan base-package="com.howtodoinjava.demo" />
<mvc:resources mapping="/image/**" location="/image/" />
<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" />
<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping" />
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/views/" />
<property name="suffix" value=".jsp" />
</bean>
<bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource">
<property name="basename" value="messages" />
</bean>
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="20848820" />
</bean>
</beans>
5. Spring MVC 视图上传文件
我已经写了两个 JSP 文件。 一个用于显示文件上传表单,用户将在其中填写其他详细信息并选择要上传的文件。 其次,我们将显示带有其他详细信息的上传文件。
productForm.jsp
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<!DOCTYPE html>
<html>
<head>
<title>Add Product Form</title>
</head>
<body>
<div id="global">
<form:form commandName="product" action="save-product" method="post" enctype="multipart/form-data">
<fieldset>
<legend>Add a product</legend>
<p>
<label for="name">Product Name: </label>
<form:input id="name" path="name" cssErrorClass="error" />
<form:errors path="name" cssClass="error" />
</p>
<p>
<label for="description">Description: </label>
<form:input id="description" path="description" />
</p>
<p>
<label for="image">Product Images: </label>
<input type="file" name="images" multiple="multiple"/>
</p>
<p id="buttons">
<input id="reset" type="reset" tabindex="4">
<input id="submit" type="submit" tabindex="5" value="Add Product">
</p>
</fieldset>
</form:form>
</div>
</body>
</html>
viewProductDetail.jsp
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html>
<head>
<title>Save Product</title>
</head>
<body>
<div id="global">
<h4>The product has been saved.</h4>
<h5>Details:</h5>
Product Name: ${product.name}<br/>
Description: ${product.description}<br/>
<p>Following files are uploaded successfully.</p>
<ol>
<c:forEach items="${product.images}" var="image">
<li>${image.originalFilename}
<img width="100" src="<c:url value="/image/"/>${image.originalFilename}"/>
</li>
</c:forEach>
</ol>
</div>
</body>
</html>
Spring MVC 多文件上传示例
当我们用http://localhost:8080/springmvcexample/product-input-form
进入浏览器时,我们得到以下屏幕:
Spring MVC 文件上传表单
我们填写详细信息并提交表格,我们将在其他页面中获取提交的详细信息和所有上传的文件:
文件成功上传
在与 spring mvc 多文件上传示例相关的评论部分中,向我提出您的问题和建议。
学习愉快!