Struts2拦截器
一、Struts2拦截器原理:
Struts2拦截器的实现原理相对简单,当请求struts2的action时,Struts 2会查找配置文件,并根据其配置实例化相对的拦截器对象,然后串成一个列表,最后一个一个地调用列表中的拦截器。
比如:应用要求用户登陆,且必须为指定用户名才可以查看系统中某个视图资源;否则,系统直接转入登陆页面。对于上面的需求,可以在每个Action的执行实际处理逻辑之前,先执行权限检查逻辑,但这种做法不利于代码复用。因为大部分Action里的权限检查代码都大同小异,故将这些权限检查的逻辑放在拦截器中进行将会更加优雅。
- Struts2拦截器是在访问某个Action或Action的某个方法,字段之前或之后实施拦截,并且Struts2拦截器是可插拔的,拦截器是AOP的一种实现.
2. 拦截器栈(Interceptor Stack)。Struts2拦截器栈就是将拦截器按一定的顺序联结成一条链。在访问被拦截的方法或字段时,Struts2拦截器链中的拦截器就会按其之前定义的顺序被调用。
二、拦截器创建:
创建拦截器主要是通过实现interceptor接口或者继承AbstractInterceptor抽象类,后者用的更多
1、实现interceptor接口的拦截器
(1)在Java Resources\src目录中创建一个数据包,包名为interceptor 。
(2)右击”interceptor“数据包在弹出的快捷菜单。
(3)选择”new ->Class“命令,创建一个类,类名为LoginInterceptor,实现”com.opensymphony.xwork2.interceptor.Interceptor“接口 。
(4)单击”Finish“按钮完成拦截器的创建,代码如下:
package interceptor;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.Interceptor;
public class LoginInterceptor implements Interceptor {
@Override
public void destroy() { // TODO Auto-generated method stub
System.out.println("拦截器销毁");
}
@Override
public void init() {
System.out.println("拦截器加载");
}
@Override
public String intercept(ActionInvocation arg0) throws Exception {
System.out.println("进入拦截器");
return null;
}
}
其中
A、Init()方法:在服务器起动的时候加载一次,并且只加载一次;
B、Destroy()方法:当拦截器销毁时执行的方法;
C、Interceptor()方法:其中里边有一个参数invocation;
其中intercept方法是拦截器的核心方法,所有安装的拦截器都会调用之个方法。
四、Struts2 拦截器详细配置
默认拦截器是在不设置任何拦截器的时候,给予默认设置的,当只要设置任何一个拦截器就会覆盖掉默认拦截器, 故此,我们需要手动设置。一旦实现了检查拦截器,就可以在所有需要实现权限控制的Action中复用上面的拦截器。为了使用该拦截器,首先在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>
<constant name="struts.enable.DynamicMethodInvocation" value="true" />
<constant name="struts.devMode" value="true" />
<package name="default" namespace="/" extends="struts-default">
<interceptors>
<!-- 配置自己的拦截器 -->
<interceptor name="auth" class="interceptor.LoginInterceptor" />
<!--配置拦截器栈 -->
<interceptor-stack name="securityStack">
<!-- 系统默认拦截器栈 若没有在我们栏截器栈中指定默认栏截器它将不会被执行-->
<interceptor-ref name="defaultStack" />
<interceptor-ref name="auth" />
</interceptor-stack>
</interceptors>
<!-- 定义一个全局的返回类型 -->
<global-results>
<result name="login">/login.html</result>
</global-results>
<action name="login" class="action.LoginAction">
</action>
<action name="download" class="action.DownloadAction">
<!-- <result name="input">/login.html</result> -->
<result type="stream">
<!-- inputName默认就是InputStream,可以省略,也可以自己修改,如改成aaa, 则Action里的方法也要改成public
InputStream getAaa() -->
<param name="inputName">InputStream</param>
<param name="contentDisposition">attachment;fileName=${fileName}</param>
</result>
<!-- 在此Action中使用拦截器 -->
<interceptor-ref name="securityStack" />
</action>
<action name="upload" class="action.UploadAction" method="upLoad">
</action>
<action name="uploads" class="action.UploadActions" method="upLoad">
</action>
</package>
</struts>