SpringMVC 中桶雀,文件的上傳,是通過 MultipartResolver 實現(xiàn)的唬复。 所以矗积,如果要實現(xiàn)文件的上傳,只要在 spring-mvc.xml 中注冊相應(yīng)的 MultipartResolver 即可盅抚。
MultipartResolver 的實現(xiàn)類有兩個:
CommonsMultipartResolver
StandardServletMultipartResolver
兩個的區(qū)別:
第一個需要使用 Apache 的 commons-fileupload 等 jar 包支持漠魏,但它能在比較舊的 servlet 版本中使用。
第二個不需要第三方 jar 包支持妄均,它使用 servlet 內(nèi)置的上傳功能柱锹,但是只能在 Servlet 3 以上的版本使用。
第一個使用步驟:
/*CommonsMultipartResolver? 上傳用到的兩個包*/
"commons-fileupload:commons-fileupload:1.3.1",
"commons-io:commons-io:2.4"
如果是maven項目的話直接導入:
commons-fileupload
commons-fileupload
1.3.1
dispatcher-servlet.xml配置:
<?xml version="1.0" encoding="UTF-8"?><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.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd"> <context:component-scan base-package="edu.nf.ch08.controller"/> <mvc:annotation-driven/> <mvc:default-servlet-handler/> <!-- 文件上傳有兩種方式丰包,一種基于Servlet3.0的上傳禁熏,一種基于 commons-upload上傳,如果使用Servlet3.0的上傳方式邑彪,可以 不需要配置MultipartResolver瞧毙,Spring默認會注冊一個 StandardServletMultipartResolver。只需要在web.xml中 啟用<multipart-config>。 如果想使用commons-upload宙彪,那么需要配置一個CommonsMultipartResolver, 且指定bean的id為multipartResolver--> <!-- 這里使用commons-upload--> <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver"> <!-- 限制文件上傳的總大芯囟(單位:字節(jié)),不配置此屬性默認不限制 --> <property name="maxUploadSize" value="104857600"/> <!-- 設(shè)置文件上傳的默認編碼--> <property name="defaultEncoding" value="utf-8"/> </bean> <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <property name="prefix" value="/WEB-INF/jsp/"/> <property name="suffix" value=".jsp"/> </bean></beans>
?web.xml:
<?xml version="1.0" encoding="UTF-8"?><web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd" version="4.0"> <!-- 請求總控器 --> <servlet> <servlet-name>dispatcher</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:dispatcher-servlet.xml</param-value> </init-param> </servlet> <servlet-mapping> <servlet-name>dispatcher</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping></web-app>
后臺java(上傳、下載)處理代碼:
package edu.nf.ch08.controller;import org.apache.commons.io.FileUtils;import org.springframework.http.HttpHeaders;import org.springframework.http.HttpStatus;import org.springframework.http.MediaType;import org.springframework.http.ResponseEntity;import org.springframework.stereotype.Controller;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.PostMapping;import org.springframework.web.multipart.MultipartFile;import org.springframework.web.servlet.ModelAndView;import java.io.File;import java.io.IOException;/** * @author wangl * @date 2018/11/2 */@Controllerpublic class UploadController { /** * 文件上傳只需要Spring傳入一個MultipartFile對象即可释漆, * 這個對象可以獲取文件相關(guān)上傳的信息悲没。 * 一個MultipartFile表示單個文件上傳,當需要上傳多個文件時 * 只需要聲明為MultipartFile[]數(shù)組即可男图。 * @return */ @PostMapping("/upload") public ModelAndView upload(MultipartFile file){ //獲取當前系統(tǒng)用戶目錄 String home = System.getProperty("user.home"); //指定上傳的文件夾目錄 File uploadDir = new File(home + "/files"); //如果目錄不存在示姿,則創(chuàng)建 if(!uploadDir.exists()){ uploadDir.mkdir(); } //獲取上傳的文件名 String fileName = file.getOriginalFilename(); //構(gòu)建一個完整的文件上傳對象 File uploadFile = new File(uploadDir.getAbsolutePath() + "/" + fileName); try { //通過transferTo方法進行上傳 file.transferTo(uploadFile); } catch (IOException e) { e.printStackTrace(); throw new RuntimeException(e.getMessage()); } //將文件名存入Model,轉(zhuǎn)發(fā)到index頁面 ModelAndView mv = new ModelAndView("index"); mv.addObject("fileName", fileName); return mv; } /** * 文件下載 * 讀取服務(wù)器本地文件并封裝為ResponseEntity對象 * 響應(yīng)客戶端,寫回的是一個字節(jié)數(shù)組 * @param fileName 文件名 * @return */ @GetMapping("/download") public ResponseEntity<byte[]> download(String fileName){ //依據(jù)文件名構(gòu)建本地文件路徑 String filePath = System.getProperty("user.home") + "/files/" + fileName; //依據(jù)文件路徑構(gòu)建File對象 File file = new File(filePath); //創(chuàng)建響應(yīng)頭對象逊笆,設(shè)置響應(yīng)信息 HttpHeaders headers = new HttpHeaders(); try { //對文件名進行重新編碼栈戳,防止在響應(yīng)頭中出現(xiàn)中文亂碼 String headerFileName = new String(fileName.getBytes("UTF-8"), "ISO-8859-1"); //設(shè)置響應(yīng)內(nèi)容處理方式為附件,并指定文件名 headers.setContentDispositionFormData("attachment", headerFileName); //設(shè)置響應(yīng)頭類型為application/octet-stream,表示是一個流類型 headers.setContentType(MediaType.APPLICATION_OCTET_STREAM); //將文件轉(zhuǎn)換成字節(jié)數(shù)組 byte[] bytes = FileUtils.readFileToByteArray(file); //創(chuàng)建ResponseEntity對象(封裝文件字節(jié)數(shù)組、響應(yīng)頭难裆、響應(yīng)狀態(tài)碼) ResponseEntity<byte[]> entity = new ResponseEntity<>(bytes, headers, HttpStatus.CREATED); //最后將整個ResponseEntity對象返回給DispatcherServlet return entity; } catch (Exception e) { e.printStackTrace(); throw new RuntimeException("文件下載失敗"); } }}
上傳文件的網(wǎng)頁html:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <h1>文件上傳</h1> <!-- 當有文件上傳時子檀,表單的enctype必須設(shè)置為multipart/form-data --> <form method="post" action="upload" enctype="multipart/form-data"> File:<input type="file" name="file"/><br/> <input type="submit" value="submit"/> </form> </body> </html>
?
?
上傳成功后轉(zhuǎn)發(fā)的jsp(下載文件)頁面:
<%-- Created by IntelliJ IDEA. User: wangl Date: 2018/11/2 Time: 09:56 To change this template use File | Settings | File Templates. --%> <%@ page contentType="text/html;charset=UTF-8" language="java" %> <html> <head> <title>Title</title> </head> <body> <a href="download?fileName=${fileName}">${fileName}</a> </body> </html>
項目結(jié)構(gòu):