Загрузка файлов с помощью Spring MVC

Загрузка файла с помощью Spring MVC

1. обзор

В предыдущих статьях мыintroduced the basics обработки форм и исследовалиform tag library в Spring MVC.

В этой статье мы сосредоточимся на том, что Spring предлагает дляmultipart (file upload) support в веб-приложениях.

Spring позволяет нам включить поддержку нескольких частей с помощью подключаемых объектовMultipartResolver. Платформа предоставляет одну реализациюMultipartResolver для использования сCommons FileUpload, а другую - для использования с анализом составных запросовServlet 3.0.

После настройкиMultipartResolver мы увидим, как загрузить один файл и несколько файлов.

Мы также коснемсяSpring Boot.

2. Файл Commons

Чтобы использоватьCommonsMultipartResolver для обработки загрузки файла, нам нужно добавить следующую зависимость:


    commons-fileupload
    commons-fileupload
    1.3.1

Теперь мы можем определить bean-компонентCommonsMultipartResolver в нашей конфигурации Spring.

ЭтотMultipartResolver поставляется с серией методовset для определения таких свойств, как максимальный размер для загрузки:

@Bean(name = "multipartResolver")
public CommonsMultipartResolver multipartResolver() {
    CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver();
    multipartResolver.setMaxUploadSize(100000);
    return multipartResolver;
}

Здесь нам нужно управлять различными свойствамиCommonsMultipartResolver в самом определении Bean.

3. With Сервлет 3.0

Чтобы использовать составной синтаксический анализServlet 3.0, нам нужно настроить пару частей приложения. 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);
    }
}

В объектеMultipartConfigElement мы настроили место хранения, максимальный размер отдельного файла, максимальный размер запроса (в случае нескольких файлов в одном запросе) и размер, при котором прогресс загрузки файла сбрасывается в место хранения.

Эти настройки должны применяться на уровне регистрации сервлета, посколькуServlet 3.0 не позволяет им регистрироваться вMultipartResolver, как в случае сCommonsMultipartResolver..

Как только это будет сделано,we can add the StandardServletMultipartResolver to our Spring configuration:

@Bean
public StandardServletMultipartResolver multipartResolver() {
    return new StandardServletMultipartResolver();
}

4. Uploading a File **

Чтобы загрузить наш файл, мы можем создать простую форму, в которой мы используем тег HTMLinput сtype='file'.

Независимо от выбранной нами конфигурации обработки загрузки, нам необходимо установить для атрибута кодирования формы значениеmultipart/form-data.. Это позволяет браузеру знать, как кодировать форму:


    
Select a file to upload

To store the uploaded file we can use a MultipartFile variable. Мы можем получить эту переменную из параметра запроса внутри метода нашего контроллера:

@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, включая имя файла, тип файла и так далее. Мы можем использовать простую HTML-страницу для отображения этой информации:

Submitted File

OriginalFileName: ${file.originalFilename}
Type: ${file.contentType}

5. Выгрузка Несколько файлов

Чтобы загрузить несколько файлов за один запрос, мы просто помещаем несколько полей входного файла в форму:


    
Select a file to upload
Select a file to upload
Select a file to upload

Нам нужно позаботиться о том, чтобы каждое поле ввода имело одно и то же имя, чтобы к нему можно было получить доступ как к массивуMultipartFile:

@RequestMapping(value = "/uploadMultiFile", method = RequestMethod.POST)
public String submit(@RequestParam("files") MultipartFile[] files, ModelMap modelMap) {
    modelMap.addAttribute("files", files);
    return "fileUploadView";
}

Теперь мы можем просто перебрать этот массив для отображения информации о файлах:

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>

    
        Spring MVC File Upload
    
    
        

Submitted Files

OriginalFileName: ${file.originalFilename}
Type: ${file.contentType}

6. Загрузка файлов с дополнительными данными формы

Мы также можем отправить дополнительную информацию на сервер вместе с загружаемым файлом. Нам просто нужно включить обязательные поля в форму:


    
Name
Email
Select a file to upload

В контроллере мы можем получить все данные формы, используя аннотацию@RequestParam:

@PostMapping("/uploadFileWithAddtionalData")
public String submit(
  @RequestParam MultipartFile file, @RequestParam String name,
  @RequestParam String email, ModelMap modelMap) {

    modelMap.addAttribute("name", name);
    modelMap.addAttribute("email", email);
    modelMap.addAttribute("file", file);
    return "fileUploadView";
}

Как и в предыдущих разделах, мы можем использовать HTML-страницу с тегамиJSTL для отображения информации.

Мы также можем инкапсулировать все поля формы в класс модели и использовать аннотацию@ModelAttribute в контроллере. Это было бы полезно, когда вместе с файлом есть много дополнительных полей. Давайте посмотрим на код:

public class FormDataWithFile {

    private String name;
    private String email;
    private MultipartFile file;

    // standard getters and setters
}
@PostMapping("/uploadFileModelAttribute")
public String submit(@ModelAttribute FormDataWithFile formDataWithFile, ModelMap modelMap) {

    modelMap.addAttribute("formDataWithFile", formDataWithFile);
    return "fileUploadView";
}

7. Загрузка файла загрузки Spring

[.hps] [result_box]#If we’re using Spring Boot, everything we’ve seen so far still applies. # #

Однако Spring Boot упрощает настройку и запуск всего без особых хлопот.

В частности,it’s not necessary to configure any servlet, как Boot зарегистрирует и настроит его для нас, при условии, что мы включим веб-модуль в наши зависимости:


    org.springframework.boot
    spring-boot-starter-web
    2.1.8.RELEASE

Мы можем найти последнюю версиюspring-boot-starter-web на Maven Central.

Если мы хотим контролировать максимальный размер загружаемого файла, мы можем отредактировать нашapplication.properties:

spring.servlet.multipart.max-file-size=128KB
spring.servlet.multipart.max-request-size=128KB

Мы также можем контролировать, включена ли загрузка файлов, и место загрузки файлов:

spring.servlet.multipart.enabled=true
spring.servlet.multipart.location=${java.io.tmpdir}

Обратите внимание, что мы использовали$\{java.io.tmpdir} для определения местоположения загрузки, чтобы мы могли использовать временное местоположение для разных операционных систем.

8. Заключение

[.hps] [result_box]#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. # #

Реализацию этого руководства можно найти вGitHub project. Когда проект запускается локально, к примеру формы можно получить доступ вhttp://localhost:8080/spring-mvc-java/fileUpload