一、文件上传的必要前提
- form表单的enctype取值必须是:multipart/form-data (默认值是:application/x-www-form-urlencoded) enctype:是表单请求正文的类型
- method属性取值必须是Post
- 提供一个文件选择域
二、文件上传环境搭建
2.1、在pom.xml中导入相关依赖
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<!--spring版本锁定-->
<spring.version>5.0.2.RELEASE</spring.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.apache.tomcat</groupId>
<artifactId>tomcat-api</artifactId>
<version>7.0.47</version>
</dependency>
<dependency>
<groupId>org.apache.tomcat</groupId>
<artifactId>tomcat-jasper-el</artifactId>
<version>7.0.47</version>
</dependency>
<!--导入文件上传的依赖jar包-->
<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.4</version>
</dependency>
</dependencies>
2.2、在web.xml中配置SpringMVC核心控制器
<web-app xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
version="3.0">
<!--编码过滤器-->
<filter>
<filter-name>encoding</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encoding</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<!--配置SpringMVC核心控制器-->
<servlet>
<servlet-name>dispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<!-- 配置Servlet的初始化参数,读取springmvc的配置文件,创建spring容器 -->
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:springmvc.xml</param-value>
</init-param>
<!-- 配置servlet启动时加载对象 -->
<load-on-startup>1</load-on-startup>
</servlet>
<!--配置springmvc过请求过滤器,/表示所有请求都经过springmvc处理-->
<servlet-mapping>
<servlet-name>dispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
2.3、配置SpringMVC核心配置文件springmvc.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:mvc="http://www.springframework.org/schema/mvc"
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/mvc
http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd">
<!-- 配置创建spring容器要扫描的包 -->
<context:component-scan base-package="com.itheima"></context:component-scan>
<!-- 配置视图解析器 -->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/pages/"></property>
<property name="suffix" value=".jsp"></property>
</bean>
<!--设置静态资源不过滤-->
<mvc:resources mapping="/css/**" location="/css/**"></mvc:resources>
<mvc:resources location="/images/" mapping="/images/**" />
<mvc:resources location="/js/" mapping="/js/**" />
<!--
配置文件上传解析器
ID的值是固定的 multipartResolver
class的值也是固定的
-->
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<!--设置上传文件的最大尺寸为10MB-->
<property name="maxUploadSize" value="10485760"></property>
</bean>
<!--SpringMVC注解驱动-->
<mvc:annotation-driven></mvc:annotation-driven>
</beans>
2.4、 编写文件上传页面upload.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false" %>
<html>
<head>
<title>文件上传</title>
</head>
<body>
<h1>springMVC方式文件上传</h1>
<form action="${pageContext.request.contextPath}/file/upload2" method="post" enctype="multipart/form-data">
文件上传:<input type="file" name="file">
<input type="submit" value="开始上传" >
</form>
<form action="${pageContext.request.contextPath}/file/fileupload2" method="post" enctype="multipart/form-data">
文件上传:<input type="file" name="upload">
<input type="submit" value="开始上传" enctype="multipart/form-data">
</form>
</body>
</html>
还有成功的界面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>成功的界面</title>
</head>
<body>
<h2>文件上传成功</h2>
</body>
</html>
2.5、编写控制层代码FileController
@Controller
@RequestMapping("/file")
public class FileController {
@RequestMapping(value = "/fileupload2")
public String fileuoload2(HttpServletRequest request, MultipartFile upload) throws Exception {
System.out.println("springmvc文件上传...");
// 使用fileupload组件完成文件上传
// 上传的位置
//String path = request.getSession().getServletContext().getRealPath("/uploads/");
String path="C:\\Users\\xioayue\\Desktop\\aa\\";
// 判断,该路径是否存在
File file = new File(path);
if(!file.exists()){
// 创建该文件夹
file.mkdirs();
}
// 说明上传文件项
// 获取上传文件的名称
String filename = upload.getOriginalFilename();
// 把文件的名称设置唯一值,uuid
String uuid = UUID.randomUUID().toString().replace("-", "");
filename = uuid+"_"+filename;
// 完成文件上传
upload.transferTo(new File(path,filename));
return "success";
}
}
三、springMVC实现多文件上传
3.1、编写文件上传页面upload.jsp
<h1>SpringMVC方式多选文件上传</h1>
<form action="${pageContext.request.contextPath }/file/multi" method="post" enctype="multipart/form-data" >
文件描述:<input type="text" name="desc"><br>
文件上传:<input type="file" name="files"><br>
文件上传:<input type="file" name="files"><br>
<input type="submit" value="开始上传">
</form>
3.2、编写服务器web层代码FileController
@RequestMapping(path="/multi",method = RequestMethod.POST)
public String upload3(MultipartFile[] files) throws Exception {
//1. 获取一个文件输出的磁盘路径
String path = "C:\\Users\\Administrator\\Desktop\\upload";
File dir = new File(path);
if(!dir.exists()){
dir.mkdir();
}
//遍历文件集合
for (MultipartFile file : files) {
//2. 获取文件名称
String filename = file.getOriginalFilename();
//3. 获取文件内容
InputStream is = file.getInputStream();//获取文件内容
//4. 创建输出流
OutputStream os = new FileOutputStream(path + "/" + filename);
//5. 将文件内容通过输出流写到磁盘文件中
int i = 0;
byte[] bys = new byte[1024];
while ((i = is.read()) != -1) {
os.write(bys, 0, i);
}
os.close();
}
return "success";
}
四、传统的文件上传
4.1、编写文件上传页面upload.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>文件上传表单</title>
</head>
<body>
<form action="${pageContext.request.contextPath }/UploadServlet" method="post" enctype="multipart/form-data" >
文件描述:<input type="text" name="fileDescribe"><br>
文件上传:<input type="file" name="file"><br>
<input type="submit" value="开始上传">
</form>
</body>
</html>
4.2、编写文件上传的控制层方法FileController
@Controller
@RequestMapping("/file")
public class FileController {
/**
* 传统方式文件上传
* @param request 请求对象 包含文件上传信息
* @param response
* @throws Exception
*/
@RequestMapping(path="/upload",method = RequestMethod.POST)
public void upload(HttpServletRequest request, HttpServletResponse response) throws Exception {
//1. 创建磁盘文件工厂
DiskFileItemFactory factory = new DiskFileItemFactory();
//2. 创建核心的解析类
ServletFileUpload upload = new ServletFileUpload(factory);
//3. 解析请求对象,获取到各个部分
List<FileItem> fileItems = upload.parseRequest(request);
//4. 获取一个文件输出的磁盘路径
String path = "C:\\Users\\Administrator\\Desktop\\upload";
File dir = new File(path);
if(!dir.exists()){
dir.mkdir();
}
//5. 遍历表单的各项
for (FileItem fileItem : fileItems) {
//6. 判断是普通项还是文件上传项
if (fileItem.isFormField()) { // 普通项
String name = fileItem.getFieldName(); //获取普通项name属性的值
String value = fileItem.getString(); //获取普通项value属性的值
System.out.println(name + " " + value);
} else { //文件上传项
String name = fileItem.getName();//获取文件名称 a.txt
InputStream is = fileItem.getInputStream();//获取文件内容
//创建输出流
OutputStream os = new FileOutputStream(path + "/" + name);
// 将文件内容通过输出流写到磁盘文件中
int i = 0;
byte[] bys = new byte[1024];
while ((i = is.read()) != -1) {
os.write(bys, 0, i);
}
os.close();
is.close();
}
}
}
}
4.3、总结
- 创建磁盘文件工厂DiskFileItemFactory factory = new DiskFileItemFactory();
- 创建核心的解析类 ServletFileUpload upload = new ServletFileUpload(factory);
- 解析文件上传的请求,获取文件上传的各个部分 List fileItems = upload.parseRequest(request);
- 遍历文件上传的各个部分,判断是一个文件上传项还是一个普通的表单项
如果是一个文件上传项,获取文件名称和文件内容,创建一个输出流将文件写到磁盘上
如果是一个普通的表单项,获取name和value就可以了