How to upload File in Spring MVC

In this article, we will understand the file upload functionality in Spring MVC. We will look at a simple example to understand it.

As we know, while creating any web application, we need to upload images or files into the system. So, Spring framework makes the thing easy for us. In Spring MVC, implementing file upload functionality is quite easy. It provides users the MultipartResolver bean that will help to resolve multipart-form data.

Like in the case of View, we have ViewResolver bean, in the same way for the file we have MultipartResolver bean

Steps to File Upload in Spring MVC:

  • First, we need to have the dependencies of ApacheCOmmonFileUpload and Commons.io.
<dependency>
            <groupId>commons-fileupload</groupId>
            <artifactId>commons-fileupload</artifactId>
            <version>1.3.1</version>
</dependency>
        <!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.10.0</version>
</dependency>
  • Next, declare MultipartResolver bean in the Spring Context file : [anyName]-servlet.xml
 <!-- Add Entry of CommonsMultipartResolver  -->
   
   <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
</bean>
  • Create a form to accept the files
<form action="save" method="post" enctype="multipart/form-data">
<label for="formFile" class="form-label">Upload File</label>
 <input class="form-control" name="file" type="file" id="formFile"><br />
<input type="submit" value="Upload">
</form>
  • Create a Controler to handle mapping and to save the image on the server.
@RequestMapping(value = "/save", method = RequestMethod.POST)
  public String saveFile(@RequestParam CommonsMultipartFile file, HttpSession session, Model model) throws IOException {
    byte[] b = file.getBytes();
    // we have to save this file to the server
    String savepath = session.getServletContext().getRealPath("/") +"WEB-INF"+File.separator+"resources"+File.separator+"img"+File.separator+file.getOriginalFilename();
    System.out.println(savepath);
    FileOutputStream fos = new FileOutputStream(savepath);
    fos.write(b);
    fos.close();
    model.addAttribute("success", "File Uploaded Successfully");
    model.addAttribute("filename", file.getOriginalFilename());
    System.out.println("File Uploaded");
    return "index";

}

Example of File Upload in Spring MVC

Create a Spring Project Go to File> New > Other > Search maven > Select Maven Project > Next > Search Filter org.apche.maven.archetypes/webapp > Next > Enter Group Id & Archetype id > Finish

pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>co</groupId>
  <artifactId>SpringMVCExample</artifactId>
  <packaging>war</packaging>
  <version>0.0.1-SNAPSHOT</version>
  <name>SpringMVCExample Maven Webapp</name>
  <url>http://maven.apache.org</url>
  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8.1</version>
      <scope>test</scope>
    </dependency>
    <dependency>
            <groupId>commons-fileupload</groupId>
            <artifactId>commons-fileupload</artifactId>
            <version>1.3.1</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.10.0</version>
</dependency>
        
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-context -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-web -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-web</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-core -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-core</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-beans -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-beans</artifactId>
      <version>5.3.5</version>
    </dependency>
    <!-- https://mvnrepository.com/artifact/javax.servlet/jstl -->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>jstl</artifactId>
      <version>1.2</version>
    </dependency>

    <!-- https://mvnrepository.com/artifact/javax.servlet.jsp/javax.servlet.jsp-api -->
    <dependency>
      <groupId>javax.servlet.jsp</groupId>
      <artifactId>javax.servlet.jsp-api</artifactId>
      <version>2.3.3</version>
      <scope>provided</scope>
    </dependency>
    <!-- https://mvnrepository.com/artifact/javax.servlet/javax.servlet-api -->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>javax.servlet-api</artifactId>
      <version>4.0.1</version>
      <scope>provided</scope>
    </dependency>
    <!-- https://mvnrepository.com/artifact/org.springframework/spring-webmvc -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>5.3.5</version>
    </dependency>
  </dependencies>
  <build>
    <finalName>SpringMVCExample</finalName>
  </build>
</project>

Create a  Web.xml file. It is a deployment descriptor that is used by the server to map the incoming request.

web.xml

<!DOCTYPE web-app PUBLIC
 "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
 "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app>
  <display-name>Archetype Created Web Application</display-name>
  <servlet>    
    <servlet-name>spring</servlet-name>    
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> 
    <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>/WEB-INF/Spring-servlet.xml</param-value>
    </init-param>   
    <load-on-startup>1</load-on-startup>      
</servlet>    
<servlet-mapping>    
    <servlet-name>spring</servlet-name>    
    <url-pattern>/</url-pattern>    
</servlet-mapping>  
</web-app>

Create a Spring-servlet.xml file.

  • Here, we have used <context:component-scan> detects the annotation by package scanning.
  • It tells Spring to scan which package to search for Controller, Beans, or any component.
  • @Component, @Controller, @Repository, @Service, @Service, and etc. are ones that <context:component-scan> can detect.
  • To resolves views such as JSP, we have used InternalResourceViewResolver.
  • Here, to resolve Photo or file, we have used MultipartReolver bean.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:context="http://www.springframework.org/schema/context"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xsi:schemaLocation="
   http://www.springframework.org/schema/beans     
   http://www.springframework.org/schema/beans/spring-beans.xsd
   http://www.springframework.org/schema/context 
   http://www.springframework.org/schema/context/spring-context.xsd">
   
   <!--  component scan -->
   <context:component-scan base-package="org.mvc.controller"></context:component-scan>
   
   <!-- Add Entry of CommonsMultipartResolver  -->
   
   <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"></bean>
  <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
  <property name="prefix" value="/WEB-INF/views/" />
      <property name="suffix" value=".jsp" />
  </bean>
   </beans>

Now, Create a Controller. The DispatcherServlet on receiving the request transfer the request to the controller.

  • The @Controller here defines the class as Controller in SpringMVC.
  • The @RequestMapping annotation maps the URL to the method.
  • The @RequestParam annotation map the form field. Here, we have mapped the ‘file’ from the form to the CommonsMultipartFile object.
  • The bean MultipartResolver will convert multipart data to this object.
package org.mvc.controller;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

import javax.servlet.http.HttpSession;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
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.multipart.commons.CommonsMultipartFile;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class HomeController {

  @RequestMapping("/")
  public String home(Model m) {
    return "index";
  }

  @RequestMapping(value = "/save", method = RequestMethod.POST)
  public String saveFile(@RequestParam CommonsMultipartFile file, HttpSession session, Model model) throws IOException {
    byte[] b = file.getBytes();
    // we have to save this file to the server
    String savepath = session.getServletContext().getRealPath("/") +"WEB-INF"+File.separator+"resources"+File.separator+"img"+File.separator+file.getOriginalFilename();
    System.out.println(savepath);
    FileOutputStream fos = new FileOutputStream(savepath);
    fos.write(b);
    fos.close();
    model.addAttribute("success", "File Uploaded Successfully");
    model.addAttribute("filename", file.getOriginalFilename());
    System.out.println("File Uploaded");
    return "index";

  }
}
  • On-Line no 30: In the saveFile() method, first the file is converted into an array of bytes.
  • On-Line no 32: We have created the path where the file will be stored.
  • On-Line no 35: The object of FileOutputStream is created to write the file to the path.
  • On-Line no 41: At last, the index page is returned with a success message.
Create a form to upload the File

index.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core"%>
<%@ taglib prefix="f" uri="http://www.springframework.org/tags/form"%>
<html>
<head>
<!-- CSS only -->
<link
  href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css"
  rel="stylesheet"
  integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC"
  crossorigin="anonymous">
<!-- JavaScript Bundle with Popper -->
<script
  src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js"
  integrity="sha384-MrcW6ZMFYlzcLA8Nl+NtUVF0sA7MsXsP1UyJoMp4YLEuNSfAP+JcXn/tWtIaxVXM"
  crossorigin="anonymous"></script>
<title>File Upload</title>
</head>
<body style="background-color: #e2e2e2">
  <h1 align="center" style="font-weight: bold; font-family: inherit;">Spring
    MVC File Upload</h1>
  <div class="container" align="center">
    <div class="card" style="width: 18rem;">
    <c:if test="${success !=null}">
    <h3 style="color:red"><c:out value="${success}"/></h3> </c:if>
      <div class="card-body">
        <h2 class="card-title">File Upload</h2>
        <div class="mb-3">
          <form action="save" method="post" enctype="multipart/form-data">
            <label for="formFile" class="form-label">Upload File</label> <input
              class="form-control" name="file" type="file" id="formFile"><br />
            <input type="submit" value="Upload" class="btn btn-warning">
          </form>
        </div>
      </div>
    </div>
  </div>
</body>
</html>

Now, Deploy the application on the server and see the following output

Thus, in this way, we upload any image or file on the server in Spring MVC.