Struts2默认拦截器栈中包含一个文件上传拦截器,其底层实现依赖apache的commons.fileUpload,网页表单则可通过Struts2的文件上传拦截器直接上传文件。
拦截器将客户端上传的文件自动存放至系统临时目录,Struts2的Action需要做的就是将临时目录中的文件通过IO流转存至指定目录。
注意:
① 文件上传时需要注意struts2-core-2.3.37.jar\org.apache.struts2\default.properties中的文件上传大小限制
② JSP页面文件上传表单form需加上enctype=“multipart/form-data”
文件上传Action:
package action;
import java.io.File;
import java.io.IOException;
import org.apache.commons.io.FileUtils;
import org.apache.struts2.ServletActionContext;
public class UploadAction {
private File[] images;
// 此处命名必须以File类型文件属性名称 + FileName结尾,否则无法识别
private String[] imagesFileName;
// 此处省略字段的Getters和Setters
public String execute() {
// 考虑images[]未创建的情况,预防未选择任何文件而直接提交时触发的空指针异常
if (null != images) {
for (int i = 0; i < images.length; i++) {
try {
// 实际Web项目无权操作客户机的文件路径,仅项目路径可供使用
String path = ServletActionContext.getServletContext().getRealPath("/images");
File destFile = new File(path, imagesFileName[i]);
FileUtils.copyFile(images[i], destFile);
} catch (IOException e) {
e.printStackTrace();
}
}
return "success";
}
return "message";
}
}
服务端向客户端发送浏览器支持的文件类型(如txt、jpg等)时会直接在浏览器中显示,反之若服务端要求用户以附件的形式保存文件则另称为文件下载。向浏览器提供文件下载功能需要设置HTTP响应头的Content-Disposition=attachment。
Action类中需要提供文件输入流(用于指定服务器向客户端提供下载的文件资源)和文件名(用户下载的资源文件名称)两个属性,struts.xml配置文件中对应Action的result标签的type宜设置为stream。
文件下载Action:
package action;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import org.apache.struts2.ServletActionContext;
public class DownloadAction {
private InputStream is;
// 此处的文件名称无需仿照文件上传时的xxxFileName,命名规范即可
private String fileName;
// 此处省略字段的Getters和Setters
public String execute() throws UnsupportedEncodingException {
fileName = "16.jpeg"; // 将项目pojoImgs下的16.jpeg作为资源下载目标
is = ServletActionContext.getServletContext().getResourceAsStream("/pojoImgs/" + fileName);
// 手动指定资源下载时的文件名称,实际宜从DB中加载
fileName = "下载测试.jpeg";
// 解决中文资源名称乱码问题:先以utf-8拆解,再以ISO-8859-1组装
byte[] bytes = fileName.getBytes("utf-8");
fileName = new String(bytes, "ISO-8859-1");
return "success";
}
}
struts.xml(重要)
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
"http://struts.apache.org/dtds/struts-2.3.dtd">
<struts>
<!-- 手动指定default.properties中总上传文件大小的限制 -->
<constant name="struts.multipart.maxSize" value="20971520"/>
<package name="strutsFiles" namespace="/upAndDownload" extends="struts-default">
<action name="uploadAction" class="action.UploadAction">
<result name="success">/welcome.jsp</result>
<result name="message">/message.jsp</result>
<!-- 指定上传文件的扩展名 -->
<interceptor-ref name="defaultStack">
<param name="fileUpload.allowedExtensions">bmp,gif,jpg,jpeg,png,webp</param>
</interceptor-ref>
</action>
<action name="downloadAction" class="action.DownloadAction">
<result type="stream">
<!-- 指定文件资源以存于Action中的fileName属性值命名 -->
<param name="contentDisposition">attachment;filename=${fileName}</param>
<!-- param标签的name属性值默认为inputName -->
<!-- 当且仅当文件下载Action中的InputStream名为inputStream时此句可省略 -->
<param name="inputName">is</param> <!-- is为文件下载Action中的InputStream名称 -->
</result>
</action>
</package>
</struts>
WebRoot目录结构:
index.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib uri="/struts-tags" prefix="s" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Index</title>
</head>
<body>
<!-- form的enctype="multipart/form-data"属性值是表单文件上传的必填选项 -->
<form action="upAndDownload/uploadAction" method="post" enctype="multipart/form-data">
请选择图片:<br /><br />
<input type="file" name="images" /><br /><br />
<input type="file" name="images" /><br /><br />
<input type="file" name="images" /><br /><br />
<input type="submit" value="上传" />
</form><br /><br />
<a href="upAndDownload/downloadAction">下载一张图片...</a>
</body>
</html>
message.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Message</title>
</head>
<body>
<h3 align="center">文件上传失败!</h3>
</body>
</html>
welcome.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Welcome</title>
</head>
<body>
<h3 align="center">文件上传成功!</h3>
</body>
</html>