Struts2学习笔记(9)-----Struts2之拦截器(上)


      经常逛论坛的人会有这样的经历:当你以“游客”的身份下载论坛帖子里的附件时会提示你“对不起,你没有权限,请登录!”,其实这就是Struts2拦截器控制权限的一个很重要的应用。


      Struts2的拦截器是一个很重要的机制,因此,得好好研究。用李刚的话说:“拦截器几乎完成了Struts2框架70%的工作,包括解析请求的参数,执行数据校验,文件上传…”,可以看出Struts2的拦截器是多么的“多才多艺”,更可以说是Struts2监视action的重要“门神”!


     Struts2内建了了大量的拦截器,这些拦截器都以“name-class”的形式保存在struts-default.xml中,因为比较多,我就不详细介绍了,如果有不解你可以在网上自己查查资料。


     下面通过一张图表去了解在执行action时拦截器被前后调用的过程,并且怎么把执行结果呈现给我们,如下所示:

Struts2学习笔记(9)-----Struts2之拦截器(上)_第1张图片

     当一个请求到达Struts 2框架,将发生以下一系列的动作:


     ①  框架首先找到哪个Action类调用这个请求,并找到与映射相关的拦截器


      ②  现在框架就创建一个ActionInvocation的实例并调用invoke()方法。这就意味着框架把控制权限交给ActionInvocation实例让它处理以后的请求。


      ③  ActionInvocation封装了action和相关联的拦截器,ActionInvocation知道哪一个拦截器应该被调用。


      ④  ActionInvocation现在调用栈里第一个拦截器intercept()方法。


      需要说明的是,建立的拦截器类需要实现Intercepor接口,这个接口有init(),destroy(),intercept(ActionInvocation invocation)这3个方法。前两个方法分别在拦截器执行之前、拦截器实例被销毁之后调用。而第三个则是用户需要实现的拦截动作。但是Struts2还提供了一个AbstractInterceptor类,该类提供了init和destroy方法的空实现,如果我们的拦截器不需要打开资源,则可以不实现这两个方法。因此继承AbstractInterceptor类会更简单。


      以前做过一个登陆的小例子(点击这里查看:Struts2学习笔记(3)-----Struts2入门),因此在以前的LoginAction的基础上来了解拦截器前后执行的过程。


      新建一个拦截器类InterceptorsUtil.java并继承AbstractInterceptor类,代码如下所示:

package com.iman.util;

import java.text.SimpleDateFormat;
import java.util.Date;

import com.iman.action.LoginAction;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.AbstractInterceptor;

public class InterceptorsUtil extends AbstractInterceptor {
	
	private String name;
	@Override
	public String intercept(ActionInvocation invocation) throws Exception {
		// TODO Auto-generated method stub
		 SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");          
		 String time=sdf.format(new Date());
		 //获得LoginAction的实例
		 LoginAction action= (LoginAction) invocation.getAction(); 
		 //打印输出拦截器开始执行的时间
		 System.out.println(name+"拦截器的动作..."+"开始执行登陆Action的时间为:"+time);
		 //为方便查看,用线程暂停3秒后在执行
		 Thread.sleep(3000);
		 //执行该拦截器的后一个拦截器,如果该拦截器后没有其他拦截器,则直接执行Action的execute方法
		 String result=invocation.invoke();
		 //打印输出执行结束的时间
		 Thread.sleep(3000);
		 System.out.println(name+"拦截器的动作..."+"执行完登陆Action的时间为:"+time);
		return result;
	}
	public String getName() {
		return name;                                                                                                                                            
	}
	public void setName(String name) {
		this.name = name;
	}
	
}
                                             	


         具体执行过程代码中已给有注释,这里就不赘述了。来配置struts.xml文件,代码如下所示:


<interceptors>
            <interceptor name="loginInter" class="com.iman.util.InterceptorsUtil">
               <param name="name">简单拦截器</param>
            </interceptor>
        </interceptors>
        <action name="login" class="com.iman.action.LoginAction"  method="login">
            <result name="success">/results/loginSuccess.jsp</result>
            <result name="error">/results/loginError.jsp</result>
            <interceptor-ref name="defaultStack"></interceptor-ref>
            <interceptor-ref name="loginInter">
               <param name="name">改名后拦截器</param>
            </interceptor-ref>
        </action>


       <interceptors  />是定义了一个拦截器,而<interceptor-ref  />则使用拦截器,<param />则给拦截器指定参数。我们也定义了一个默认的拦截器,并配置参数。


     好了,由于这个登陆例子前面也已经展示过了,这里就不在编写了,只是在LoginAction.java的登陆方法中打印输出一句“进入登陆Action中的方法......”作为标记,打开服务器并部署项目,运行login.jsp页面,当我们输入了用户登录信息后eclipse控制台输出了:


改名后拦截器拦截器的动作...开始执行登陆Action的时间为:2011-12-17 16:24:33

进入登陆Action中的方法......

改名后拦截器拦截器的动作...执行完登陆Action的时间为:2011-12-17 16:24:33


如下所示:

       Struts2学习笔记(9)-----Struts2之拦截器(上)_第2张图片

  

     可以看出,在执行登陆的action之前,首先进入自定义的拦截器中,对LoginAction执行方法进行拦截,执行完登陆action后又返回到这个拦截器中,可以从控制台中看出来。                                                                                                                                                                                                                                                                                                                                                                                  

     另外我们在struts.xml配置文件中都配置了name参数,但是在拦截器类中只调用了“改名后拦截器”而不是“简单拦截器”,说明<interceptor-ref />覆盖了<interceptor/>


      从这个例子看出来Struts2的拦截器功能非常强大,它既可以在Action的调用方法之前插入执行代码,也可以在调用方法之后执行代码,这种方法的实质就是AOP(面向切面编程)思想。那么现在看来,开头的那个控制下载权限的问题不就迎刃而解了!


    这是本人学习的结果,欢迎转载,欢迎交流,但转载务必给出本文章的链接地址:http://blog.csdn.net/youqishini/article/details/7080237,谢谢~ 


 


你可能感兴趣的:(exception,框架,struts,String,Interceptor,action)