struts2之文件上传

struts2对文件的上传进行了封装,主要核心是FileUploadInterceptor拦截器对文件上传请求的操作,那么对于文件上传的实现,我们开发或者需要注意哪些呢?

我们先来大概解析一下FileUploadInterceptor拦截器对应的javadoc文档:

Open Declaration org.apache.struts2.interceptor.FileUploadInterceptor
/*
 * FileUploadInterceptor拦截器是基于MultiPartRequestWrapper,将会拦截所有包含文件的请求
 * 以下是所要求参数格式
 */
Interceptor that is based off of MultiPartRequestWrapper, which is automatically applied for any request that 
includes a file. It adds the following parameters, where [File Name] is the name given to the file uploaded 
by the HTML form: 
//所要上传的文件(自定义名字)
[File Name] : File - the actual File 
//所上传文件的内容类型
[File Name]ContentType : String - the content type of the file 
//所上传文件的真实文件名
[File Name]FileName : String - the actual name of the file uploaded (not the HTML name) 

/*
 * 可以在Action类中提供setter方法获取这些文件
 */
You can get access to these files by merely providing setters in your action that correspond to any of the 
three patterns above, such as setDocument(File document), setDocumentContentType(String contentType), etc. 
See the example code section. 

/*
 * 如果Action类实现了ValidationAware,FileUploadInterceptor拦截器将会加入错误消息,这些消息是默认的
 * 国际化消息,可以通过以下方式覆盖
 */
This interceptor will add several field errors, assuming that the action implements ValidationAware. These 
error messages are based on several i18n values stored in struts-messages.properties, a default i18n file 
processed for all i18n requests. You can override the text of these messages by providing text for the 
following keys: 
//通常文件上传出错的消息
struts.messages.error.uploading - a general error that occurs when the file could not be uploaded 
//上传文件超过最大值
struts.messages.error.file.too.large - occurs when the uploaded file is too large 
//上传的文件内容不合法
struts.messages.error.content.type.not.allowed - occurs when the uploaded file does not match the expected 
content types specified 
//上传文件的扩展名不合法
struts.messages.error.file.extension.not.allowed - occurs when the uploaded file does not match the expected 
file extensions specified 

/*
 * 通过配置 FileUploadInterceptor 拦截器的参数的方式来进行限制
 */
Interceptor parameters: 
//以字节为单位,默认的最大值为2M
maximumSize (optional) - the maximum size (in bytes) that the interceptor will allow a file reference to be 
set on the action. Note, this is not related to the various properties found in struts.properties. Default to 
approximately 2MB. 
//允许的上传文件的类型. 多个使用 ","分割.如果没有指定,拦截器将会在Action类中设置文件参考
allowedTypes (optional) - a comma separated list of content types (ie: text/html) that the interceptor will 
allow a file reference to be set on the action. If none is specified allow all types to be uploaded. 
//允许的上传文件的扩展名. 多个使用 , 分割.
allowedExtensions (optional) - a comma separated list of file extensions (ie: .html) that the interceptor 
will allow a file reference to be set on the action. If none is specified allow all extensions to be 
uploaded. 

/*
 * 扩展拦截器
 */
Extending the interceptor: 

You can extend this interceptor and override the acceptFile method to provide more control over which files 
are supported and which are not. 

Example code: //实例代码

 <action name="doUpload" class="com.example.UploadAction">
     <interceptor-ref name="fileUpload"/>
     <interceptor-ref name="basicStack"/>
     <result name="success">good_result.jsp</result>
 </action>
 
/*
 * 在文件上传的表单中必须做如下设置
 */
You must set the encoding to multipart/form-data in the form where the user selects the file to upload. 

   <s:form action="doUpload" method="post" enctype="multipart/form-data">
       <s:file name="upload" label="File"/>
       <s:submit/>
   </s:form>

其实文档中还有Action类的示例,在这里省去,将在下面的例子中讨论。根据上面的文件描述,用一个例子示范:

Action类:

这里须注意一点:File对应的参数名可以自定义,但是ContentType和FileName必须在之前加上定义的文件参数名。如:自定义文件名是[fileFieldName],那么其他两个参数必须是:[fileFieldName]ContentType和[fileFieldName]FileName。

import java.io.File;

import com.opensymphony.xwork2.ActionSupport;

public class FileUploadAction extends ActionSupport {

	private static final long serialVersionUID = 1L;

	private File test;
	private String testContentType;
	private String testFileName;
	
	public File getTest() {
		return test;
	}
	public void setTest(File test) {
		this.test = test;
	}
	public String getTestContentType() {
		return testContentType;
	}
	public void setTestContentType(String testContentType) {
		this.testContentType = testContentType;
	}
	public String getTestFileName() {
		return testFileName;
	}
	public void setTestFileName(String testFileName) {
		this.testFileName = testFileName;
	}
	
	@Override
	public String execute() throws Exception {
		
		System.out.println(test);
		System.out.println(testContentType);
		System.out.println(testFileName);
		
		return super.execute();
	}
}
jsp页面:

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
    <%@taglib prefix="s" uri="/struts-tags" %>
<!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>Insert title here</title>
</head>
<body>
	<!-- 须设置enctype属性为"multipart/form-data" -->
	<s:form action="fileUpload" method="post" enctype="multipart/form-data">
		<!-- struts2中文件选择要用 s:file标签 -->
		<s:file name="test" label="file"></s:file>
		<s:submit></s:submit>
	</s:form>
</body>
</html>
国际化文件globalMessage.properties中配置消息:

struts.messages.error.uploading=\u6587\u4ef6\u4e0a\u4f20\u51fa\u9519\u7684\u6d88\u606f
struts.messages.error.file.too.large=\u6587\u4ef6\u8d85\u8fc7\u6700\u5927\u503c\u7684\u6d88\u606f
struts.messages.error.content.type.not.allowed=\u6587\u4ef6\u5185\u5bb9\u7c7b\u578b\u4e0d\u5408\u6cd5\u7684\u6d88\u606f
struts.messages.error.file.extension.not.allowed=\u6587\u4ef6\u6269\u5c55\u540d\u4e0d\u5408\u6cd5\u7684\u6d88\u606f
在struts.xml配置拦截器栈和action:

在struts.xml文件中,对package标签下元素配置必须按照这个顺序:result-types、interceptors、default-interceptor-ref、default-action-ref、default-class-ref、global-results、global-exception-mappings、action*,也就是说上面的testStack必须在action之前配置。否则会报错,并提示:The content of element type "package" must match "(result-types?,interceptors?,default-interceptor-ref?,default-action-ref?,default-class-ref?,global-results?,global-exception-mappings?,action*)".

<?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>

	<!-- 配置国际化资源文件-->
	<constant name="struts.custom.i18n.resources" value="globalMessage"></constant>
	<!-- 设置临时存放文件夹,用于文件上传 -->
	 <constant name="struts.multipart.saveDir" value="/tmp"></constant>
	 
    <package name="default" namespace="/" extends="struts-default">
    	
    	<interceptors>
       		<!-- 自定义拦截器栈,即在默认拦截器栈的基础上添加params -->
       		<interceptor-stack name="testStack">
       			<interceptor-ref name="defaultStack">
       				<!-- 设置上传文件的最大值 -->
       				<param name="fileUpload.maximumSize">2097152</param>
       				<!-- 规定上传文件的内容格式 -->
					<param name="fileUpload.allowedTypes">text/html,text/xml</param>
					<!-- 规定上传文件的后缀名 -->
					<param name="fileUpload.allowedExtensions">html,dtd,xml</param>
       			</interceptor-ref>
       		
       		</interceptor-stack>
       
       </interceptors>
    
        <action name="fileUpload" class="com.fileupload.action.FileUploadAction">
        	<result name="success">/success.jsp</result>
        	<result name="input">/upload.jsp</result>
        	<!-- 在action中引入自定义拦截器 -->
        	<interceptor-ref name="testStack"></interceptor-ref>
        </action>
       
    </package>

</struts>

运行结果,当上传的文件与拦截器中配置的参数不符的时候:


在struts2中可以同时上传多个文件,在上述Action类中,将三个参数改为List类型的即可。

你可能感兴趣的:(文件上传,struts2)