1、文件上传的回顾
文件上传的必要前提:
- form 表单的 enctype 取值必须是:multipart/form-data(默认值是application/x-www-form-urlencoded)。enctype 是表单请求正文的类型。
- method 属性取值必须是 Post
- 提供一个文件选择域
<input type="file" />
文件上传的原理分析:
- 当 form 表单的 enctype 取值不是默认值后,request.getParameter() 将失效。
- enctype="application/x-www-form-urlencoded"时,form 表单的正文内容是:key=value&key=value&key=value
- 当 form 表单的 enctype 取值为 MultiPart/form-data时,请求正文的内容就变成:每一部分都是 MIME 类型描述的正文:
----------------------------------7dela433602ac 分界符 Content-Disposition:form-data; name="username" 协议头
借助第三方组件实现文件上传:
- 使用 Commons-fileupload 组件实现文件上传,需要导入该组件相应的支撑 jar 包:Commons-fileupload 和 commons-io。
2、SpringMVC 传统方式实现文件上传
1、添加依赖包:commons-fileupload、commons-io
<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>
2、编写前端页面:
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h3>文件上传</h3>
<form action="./user/fileUpload1" method="post" enctype="multipart/form-data">
选择文件:<input type="file" name="upload" /> <br/>
<input type="submit" value="上传">
</form>
</body>
</html>
3、编写后端解析代码:
/**
* 文件上传
* @return
*/
@RequestMapping("/fileUpload1")
public String fileUpload(HttpServletRequest request) throws Exception {
//使用fileupload组件完成文件上传
String path = request.getSession().getServletContext().getRealPath("/uploads/");
System.out.println(path);
//判断,该路径是否存在
File file = new File(path);
if(!file.exists()) {
file.mkdirs();
}
// 解析request对象,获取上传文件项
DiskFileItemFactory factory = new DiskFileItemFactory();
ServletFileUpload fileUpload = new ServletFileUpload(factory);
//解析request
List<FileItem> fileItems = fileUpload.parseRequest(request);
//遍历
for(FileItem item : fileItems) {
//进行判断,当前item对象是否是上传文件项
if(item.isFormField()){
//说明是普通表单项
} else {
//说明是上传文件项
//获取上传文件的名称
String filename = item.getName();
String uuid = UUID.randomUUID().toString().replace("-", "");
filename = uuid + "_" + filename;
//完成文件上传
item.write(new File(file, filename));
//删除临时文件
item.delete();
}
}
return "success";
}
3、SpringMVC 方式实现文件上传
1、在 spring.xml 中配置文件解析器:
<!-- 配置文件解析器对象 -->
<!-- 这个bean的id名必须为multipartResolver -->
<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="10485760" /> <!-- 最大上传大小 -->
</bean>
2、编写前端控制器代码:
<h3>SpringMVC方式文件上传</h3>
<form action="./user/fileUpload2" method="post" enctype="multipart/form-data">
选择文件:<input type="file" name="upload"/> <br/>
<input type="submit" value="上传">
</form>
2、编写控制器代码:
/**
*
* @param request
* @param upload 这个名字必须跟表单文件项的名字一致!!
* @return
*/
@RequestMapping("/fileUpload2")
public String fileUpload2(HttpServletRequest request, MultipartFile upload) throws IOException {
String path = request.getSession().getServletContext().getRealPath("/upload/");
File file = new File(path);
if(!file.exists()) {
file.mkdirs();
}
System.out.println(file.getAbsoluteFile());
//获得文件名称
String fileName = upload.getOriginalFilename();
//把名字变成唯一值
String uuid = UUID.randomUUID().toString().replace("-", "");
fileName = uuid + "-" + fileName;
//完成文件上传
upload.transferTo(new File(file, fileName));
return "success";
}
跨服务器方式的文件上传
1、分服务器的目的:
在实际开发中,我们会有很多处理不同功能的服务器,例如:
- 应用服务器:负责部署我们的应用
- 数据库服务器:运行我们的数据库
- 缓存和消息服务器:负责处理大并发访问的缓存和消息
- 文件服务器:负责存储用户上传文件的服务器
2、步骤:
① 创建一个新的 tomcat 项目,作为接受文件的服务器,要求端口号要变一下:
并且,需要在 D:\Java\apache-tomcat-9.0.40\webapps\fileuploadServer_war 文件夹下新建 uploads 文件夹,后续文件上传到这里。
② 在客户端服务器上(也就是另一个 tomcat 服务器)添加新的 jar 包:jersey-core、jersey-client
<dependency>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-client</artifactId>
<version>1.18.1</version>
</dependency>
<dependency>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-core</artifactId>
<version>1.18.1</version>
</dependency>
③ 编写前端代码:
<h3>跨服务器文件上传</h3>
<form action="./user/fileUpload3" method="post" enctype="multipart/form-data">
选择文件:<input type="file" name="upupload"/> <br/>
<input type="submit" value="上传">
</form>
④ 编写后端代码:
/**
* 跨服务器文件上传
* @param upupload
* @return
* @throws IOException
*/
@RequestMapping("/fileUpload3")
public String fileUpload3(MultipartFile upupload) throws IOException {
//定义上传文件服务器的路径
String path = "http://localhost:9090/fileuploadServer_war/uploads/";
String fileName = upupload.getOriginalFilename();
String uuid = UUID.randomUUID().toString().replace("-", "");
fileName = uuid + "-" + fileName;
//创建客户端对象
Client client = Client.create();
//和图片服务器进行连接
WebResource webResource = client.resource(path + fileName);
//上传图片和文件
webResource.put(upupload.getBytes());
return "success";
}