I usually post about Dev stuff on Twitter - you can follow me there:
Follow @baeldung1. Overview
In previous articles, we introduced the basics of form handling and explored the form tag library in Spring MVC.
In this article, we focus on what Spring offers for multipart (file upload) support in web applications.
Spring allows us to enable this multipart support with pluggable MultipartResolver objects. The framework provides one MultipartResolver implementation for use with Commons FileUpload and another for use with Servlet 3.0 multipart request parsing.
After configuring the MultipartResolver we’ll see how to upload single file and multiple files.
2. Commons FileUpload
To use CommonsMultipartResolver to handle the file upload, we need to add the following dependency:
<dependency> <groupId>commons-fileupload</groupId> <artifactId>commons-fileupload</artifactId> <version>1.3.1</version> </dependency>
Now we can define the CommonsMultipartResolver bean into our Spring configuration.
This MultipartResolver comes with a series of set method to define properties such as the maximum size for uploads:
@Bean(name = "multipartResolver") public CommonsMultipartResolver multipartResolver() { CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver(); multipartResolver.setMaxUploadSize(100000); return new CommonsMultipartResolver(); }
3. With Servlet 3.0
In order to use Servlet 3.0 multipart parsing, we need configure a couple pieces of the application. First, we need to set a MultipartConfigElement in our DispatcherServlet registration:
public class MainWebAppInitializer implements WebApplicationInitializer { private String TMP_FOLDER = "/tmp"; private int MAX_UPLOAD_SIZE = 5 * 1024 * 1024; @Override public void onStartup(ServletContext sc) throws ServletException { ServletRegistration.Dynamic appServlet = sc.addServlet("mvc", new DispatcherServlet( new GenericWebApplicationContext())); appServlet.setLoadOnStartup(1); MultipartConfigElement multipartConfigElement = new MultipartConfigElement(TMP_FOLDER, MAX_UPLOAD_SIZE, MAX_UPLOAD_SIZE * 2, MAX_UPLOAD_SIZE / 2); appServlet.setMultipartConfig(multipartConfigElement); } }
In the MultipartConfigElement object, we have configured the storage location, maximum individual file size, maximum request size (in case of multiple files in a single request), and the size at which the file upload progress is flushed to the storage location.
These settings must be applied at the servlet registration level, as Servlet 3.0 does not allow them to be registered in the MultipartResolver as is the case with CommonsMultipartResolver.
Once this is done, we can add the StandardServletMultipartResolver to our Spring configuration:
@Bean public StandardServletMultipartResolver multipartResolver() { return new StandardServletMultipartResolver(); }
4. Uploading a File
To upload our file, we can build a simple form in which we use an HTML input tag with type=’file’.
Regardless of the upload handling configuration we have chosen, we need to set the encoding attribute of the form to multipart/form-data. This lets the browser know how to encode the form:
<form:form method="POST" action="/spring-mvc-xml/uploadFile" enctype="multipart/form-data"> <table> <tr> <td><form:label path="file">Select a file to upload</form:label></td> <td><input type="file" name="file" /></td> </tr> <tr> <td><input type="submit" value="Submit" /></td> </tr> </table> </form>
To store the uploaded file we can use a MultipartFile variable. We can retrieve this variable from the request parameter inside our controller’s method:
@RequestMapping(value = "/uploadFile", method = RequestMethod.POST) public String submit(@RequestParam("file") MultipartFile file, ModelMap modelMap) { modelMap.addAttribute("file", file); return "fileUploadView"; }
The MultipartFile class provides access to details about the uploaded file, including file name, file type, and so on. We can use a simple HTML page to display this information:
<h2>Submitted File</h2> <table> <tr> <td>OriginalFileName:</td> <td>${file.originalFilename}</td> </tr> <tr> <td>Type:</td> <td>${file.contentType}</td> </tr> </table>
5. Uploading Multiple Files
To upload multiple files in a single request, we simply put multiple input file fields inside the form:
<form:form method="POST" action="/spring-mvc-java/uploadMultiFile" enctype="multipart/form-data"> <table> <tr> <td>Select a file to upload</td> <td><input type="file" name="files" /></td> </tr> <tr> <td>Select a file to upload</td> <td><input type="file" name="files" /></td> </tr> <tr> <td>Select a file to upload</td> <td><input type="file" name="files" /></td> </tr> <tr> <td><input type="submit" value="Submit" /></td> </tr> </table> </form:form>
We need to take care that each input field has the same name, so that it can be accessed as an array of MultipartFile:
@RequestMapping(value = "/uploadMultiFile", method = RequestMethod.POST) public String submit(@RequestParam("files") MultipartFile[] files, ModelMap modelMap) { modelMap.addAttribute("files", files); return "fileUploadView"; }
Now, we can simply iterate over that array to display files informations:
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <html> <head> <title>Spring MVC File Upload</title> </head> <body> <h2>Submitted Files</h2> <table> <c:forEach items="${files}" var="file"> <tr> <td>OriginalFileName:</td> <td>${file.originalFilename}</td> </tr> <tr> <td>Type:</td> <td>${file.contentType}</td> </tr> </c:forEach> </table> </body> </html>
6. Conclusion
In this article we looked at different ways to configure multipart support in Spring. Using these, we can support file uploads in our web applications.
The implementation of this tutorial can be found in a GitHub project. When the project runs locally, the form example can be accessed at: http://localhost:8080/spring-mvc-java/fileUpload