本文以struts2.3.16.1为例。
一、运行jar包
A.asm-3.3.jar
B.asm-commons-3.3.jar
C.commons-fileupload-1.3.1.jar(文件上传必须插件)
D.commons-io-2.2.jar(文件上传必须插件)
E.commons-lang3-3.1.jar
F.freemarker-2.3.19.jar
G.javassist-3.11.0.GA.jar
H.ognl-3.0.6.jar
I.struts2-convention-plugin-2.3.16.1.jar(使用Annotation必须有些插件)
J.struts2-core-2.3.16.1.jar
K.xwork-core-2.3.16.1.jar
web.xml添加如下配置
<filter>
<filter-name>struts2</filter-name>
<filter-class>
org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter
</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
struts常量,配置文件读取顺序:
1.struts-default.xml
2.struts-plugin.xml
3.struts.xml
4.struts.properties
5.web.xml
二、OGNL(对象图导航语言)
记录如下几种页面从Action中取值的情况。
1、访问static属性:
<s:property value="@com.bean.StaticClass@STR"/><br>
2、访问static方法:
<constant name="struts.ognl.allowStaticMethodAccess" value="true"/>
<s:property value="@com.bean.StaticClass@static_method()"/><br>
3、访问math函数:
<s:property value="@@max(2,3)"/><br>
4、访问List:
<s:property value="list"/><br>
5、访问List某个元素:
<s:property value="list[1]"/><br>
6、访问List元素某个属性的集合:
<s:property value="list.{property}"/><br>
7、访问List元素某个属性的集合中的特定值:
<s:property value="lsit[0].property"/>
8、访问set:
<s:property value="set"/><br>
访问set中某个元素(不能访问到,set无序):
<s:property value="set[1]"/><br>
9、访问Map:
<s:property value="map"/><br>
10、访问Map某个元素:
<s:property value="map.key"/><br>
11、访问Map所有的key:
<s:property value="map.keys"/><br>
12、访问Map所有的value:
<s:property value="map.values"/><br>
三、类型转换
Struts2类型转换,对于8个基本类型和Date,String,由系统自动转换,对于用户自定义的对象,需要用户自定转换。
1、自定义转换类继承DefaultTypeConverter或者StrutsTypeConverter,建议用后者。
2、在Action所在文件夹建xxx-conversion.properties,例如Action为SampleAction,则 属性文件为SampleAction-convertion.properties。
3、假设SampleAction中有自定义对象User user,则属性文件内容为:
user=com.xxx.xxx.SampleAction-convertion.propeties
4、如果是全局类型转换,则属性名称为xwork-convertion.properties,且些文件要放置在src目录下。
四、防止表单重复提交
1、重定向。result返回类型为redirect,如果采用dispatch,地址栏URL不变,会导致数据的重复插入。
2、通过session token。
原理:客户端请求页面,服务器会通会Token标签生成一个随机数,且将该随机数放置在session中,然后将该随机数发向客户端。如果第一次提交,服务器会与客户端比较,相同,则认为第一次提交,并且更新服务器的随机数值;如果再次提交,两个随机数值不一致,则认为是重复提交。
a.在<form>表单中加
<s:token></s:token>
b.在action配置中加入:
<result name="invalid.token" location="error.jsp">
<interceptor-ref name="token"/>
<!-- 必须加上默认的栈,否则其它的拦截器就失效了 -->
<interceptor-ref name="defaultstack"/>
五、文件上传
struts2通过拦截器FileUploadInterceptor处理文件上传。它会先将文件上传至临时目录,在Action中定义的file变量会指向临时目录文件,再由用户转向指定的文件目录,方法执行完毕后删除临时文件。相关配置变量:struts.multipart.savedir指定临时保存目录,如果该目录没有指定,则会保存在javax.servlet.context.tempdir目录下。其它相关配置可以在struts-default.properties寻找。
1.JSP页面Form表单:
method="post" enctype="multitype/form-data"
2.Action中定义相关变量。
private File file;
private String fileFileName;
private fileContentType;
如果页面有多个文件上传,则action定义如下
private List<File> file;
private List<String> fileFileName;
private List<String> fileContentType;
六、文件下载
struts2文件下载通过拦截器StreamResult处理。
1.JSP页面直接用
<a href="download.action">文件下载</a>
2.Action配置。参数“contentDisposition”必须要加上"attachment",如果不加,则默认为内联,浏览器默认会打开文件。
@Action(value="downloadAction",results=
{@Result(name="success",type="stream",
params={"inputName","downloadFile",
"contentDisposition","attachment;filename=${filename}"})})
3.Action中实现方法
定义成员变量filename;
private String filename;
public InputStream getDownloadFile(){
filename="根据具体情况取值";
ServletActionContext.getServletContext().
getResourceAsStream("文件路径名");
}
七、Struts2 Ajax
Struts2在JSP页面采用ajax方式调用时,Action不需要配置返回值,直接返回null。
1、返回XML代码
HttpServletResponse response = ServletActionContext.getResponse();
response.setContentType("text/xml;charset=utf-8");
response.setHeader("cache-control","no-cache");
PrintWriter out = response.getWriter();
OutputFormat format = OutputFormat.creatPrettyPrint();
format.setEncoding("utf-8");
XmlWriter writer = new XmlWriter(out,format);
writer.writer(document);
out.flush();
out.close();
return null;
2、返回JSON
HttpServletResponse response = ServletActionContext.getResponse();
response.setContentType("application/json;charset=utf-8");
response.setHeader("cache-control","no-cache");
PrintWriter out = response.getWriter();
out.writer(document);
out.flush();
out.close();
return null;
八、struts2处理JSON的另一种方式
通过struts2插件处理。插件为struts2-json-plugin-2.2.1.jar
1.struts.xml中,package必须要继承"json-default"(json-default已经继承了struts-default)。
2.Action配置返回result时,type="json"
3.在Action中定义成员变量,生成get,set方法。
4.在配置result时,其中有个参数excludeProperties,可以排除某些指定的属性生成json。
九、struts拦截器
struts2中有两种拦截器,一种可以用来拦截所有的请求,暂且叫对象拦截器吧,另一种可以用来拦截指定的方法。
对象拦截器:
1.拦截器实现Interceptor或者继承AbstractInterceptor。
2.在struts.xml中配置拦截器信息
<interceptors>
<interceptor name="interceptor1"
class="com.interceptor.Interceptor1"></interceptor>
</interceptors>
3.在Action中引用配置的拦截器
interceptorRefs={@InterceptorRef("interceptor1")}
方法拦截器:
1.拦截器实现MethodFilterInterceptor.
2.在struts.xml中配置拦截器信息
<interceptor name="methodInterceptor"
class="com.interceptor.MethodInterceptor">
<param name="includeMethods">login</param>
<param name="excludeMethods">login</param>
</interceptor>
3.在Action中引用配置的拦截器
interceptorRefs={@InterceptorRef("methodInterceptor")}
4.对于includeMethods和excludeMethods两个参数。
a.如果includeMethods指定要拦截的方法,则只会拦截指定的方法。
b.如果excludeMethods指定了不需要拦截的方法,则不会拦截指定的方法。
c.如果同一个方法同时出现在上面的两个参数中,则includeMethods优先级大于excludeMethos.
5.Struts2 拦截器处理普通Http请求和Ajax请求时拦截配置。只能处理http请求,处理ajax请求时,会将JSP以字符串形式返回。参考文章:
http://blog.csdn.net/will_awoke/article/details/16940939
十、其它
1.struts action中可以直接定义属性,也可以定义对象,或者实现model driven来获取页面对应的属性值。
2.session获取。
a.ServletActionContext.getRequest().getSession()
b.ActionContext.getContext().getSession().返回map<String,String>.这样返回与上面一致,此方法脱离了容器获取值,对单元测试时有效。
3.form表单提交动态绑定方法。需要将属性strtus.enable.DynamicMethodInvocation=true
如:login!login.action(!后面的login为执行的方法名)
属性struts.action.extension规定后缀,默认为action.
4.struts标签。struts-tag.tld位于struts-core-2.3.16.jar/META-INF/struts-tags.tld
<%@ taglib prefix="s" uri="/struts-tags"%>
5.Struts ValueStack Debug,查看值栈里的内容
a.页面上加上标签
<s:debug></s:debug>
b.配置文件
<constant name="struts.devMode" value="true" />