都督

导航

Struts2的拦截器(Interceptor)

 什么是拦截器。

    Interceptor(以下译为拦截器)是Struts 2的一个强有力的工具,有许多功能(feature)都是构建于它之上,如国际化、校验等。

    拦截器,在AOP(Aspect-Oriented Programming)中用于在某个方法或字段被访问之前,进行拦截然后在之前或之后加入某些操作。拦截是AOP的一种实现策略。在Webwork的中文文档的解释为——拦截器是动态拦截Action调用的对象。它提供了一种机制可以使开发者可以定义在一个action执行的前后执行的代码,也可以在一个action执行前阻止其执行。同时也是提供了一种可以提取action中可重用的部分的方式。

谈到拦截器,还有一个词大家应该知道——拦截器栈(Interceptor Chain,在Struts 2中称为拦截器栈Interceptor Stack)。拦截器栈就是将拦截器按一定的顺序联结成一个栈。在访问被拦截的方法或字段时,拦截器链中的拦截器就会按其之前定义的顺序被调用。

    

实现原理

Struts 2的拦截器实现相对简单。当请求到达Struts 2的ServletDispatcher时,Struts 2会查找配置文件,并根据其配置实例化相对的拦截器对象,然后串成一个列表(list),最后一个一个地调用列表中的拦截器,如图1所示。

图1 拦截器调用序列图
图1 拦截器调用序列图

STRUTS2内建拦截器

Struts 2已经为您提供丰富多样的,功能齐全的拦截器实现。大家可以到struts2-all-2.0.1.jar或struts2-core-2.0.1.jar包的struts-default.xml查看关于默认的拦截器与拦截器链的配置。

以下部分就是从struts-default.xml文件摘取的内容:

< interceptor name ="alias" class ="com.opensymphony.xwork2.interceptor.AliasInterceptor" />
< interceptor name ="autowiring" class ="com.opensymphony.xwork2.spring.interceptor.ActionAutowiringInterceptor" />
< interceptor name ="chain" class ="com.opensymphony.xwork2.interceptor.ChainingInterceptor" />
< interceptor name ="conversionError" class ="org.apache.struts2.interceptor.StrutsConversionErrorInterceptor" />
< interceptor name ="createSession" class ="org.apache.struts2.interceptor.CreateSessionInterceptor" />
< interceptor name ="debugging" class ="org.apache.struts2.interceptor.debugging.DebuggingInterceptor" />
< interceptor name ="external-ref" class ="com.opensymphony.xwork2.interceptor.ExternalReferencesInterceptor" />
< interceptor name ="execAndWait" class ="org.apache.struts2.interceptor.ExecuteAndWaitInterceptor" />
< interceptor name ="exception" class ="com.opensymphony.xwork2.interceptor.ExceptionMappingInterceptor" />
< interceptor name ="fileUpload" class ="org.apache.struts2.interceptor.FileUploadInterceptor" />
< interceptor name ="i18n" class ="com.opensymphony.xwork2.interceptor.I18nInterceptor" />
< interceptor name ="logger" class ="com.opensymphony.xwork2.interceptor.LoggingInterceptor" />
< interceptor name ="model-driven" class ="com.opensymphony.xwork2.interceptor.ModelDrivenInterceptor" />
< interceptor name ="scoped-model-driven" class ="com.opensymphony.xwork2.interceptor.ScopedModelDrivenInterceptor" />
< interceptor name ="params" class ="com.opensymphony.xwork2.interceptor.ParametersInterceptor" />
< interceptor name ="prepare" class ="com.opensymphony.xwork2.interceptor.PrepareInterceptor" />
< interceptor name ="static-params" class ="com.opensymphony.xwork2.interceptor.StaticParametersInterceptor" />
< interceptor name ="scope" class ="org.apache.struts2.interceptor.ScopeInterceptor" />
< interceptor name ="servlet-config" class ="org.apache.struts2.interceptor.ServletConfigInterceptor" />
< interceptor name ="sessionAutowiring" class ="org.apache.struts2.spring.interceptor.SessionContextAutowiringInterceptor" />
< interceptor name ="timer" class ="com.opensymphony.xwork2.interceptor.TimerInterceptor" />
< interceptor name ="token" class ="org.apache.struts2.interceptor.TokenInterceptor" />
< interceptor name ="token-session" class ="org.apache.struts2.interceptor.TokenSessionStoreInterceptor" />
< interceptor name ="validation" class ="com.opensymphony.xwork2.validator.ValidationInterceptor" />
< interceptor name ="workflow" class ="com.opensymphony.xwork2.interceptor.DefaultWorkflowInterceptor" />
< interceptor name ="store" class ="org.apache.struts2.interceptor.MessageStoreInterceptor" />
< interceptor name ="checkbox" class ="org.apache.struts2.interceptor.CheckboxInterceptor" />
< interceptor name ="profiling" class ="org.apache.struts2.interceptor.ProfilingActivationInterceptor" />

 工具拦截器

    首先,我们先看一些公具拦截器。这些拦截器提供了辅助看法,调优以及解决问题的简单工具。

           1.timer拦截器

              这个简单的拦截器只记录执行花费的时间。在拦截器栈中的位置决定了它实际测量了什么时间。

          2.logger拦截器

              这个拦截器提供了一个简单的日志记录,记录了在预处理时的进入声明,以及在后加工时的退出声明。

数据转移拦截器

           拦截器能够用来处理数据转移,通过拦截器可以将数据转移到动作上,例如从XML配置文件中的定义的参数。

           1.param拦截器

             他将请求参数转移到通过valuestack公开的属性上,拦截器不知道这些数据终究去到哪里,它只是把数据转移到valuestack上一个匹配的属性上。

           2.static-param拦截器

             它的作用和param拦截器的作用相似,不同的是参数的来源,这个拦截器转移的参数定义在声明性架构的动作元素中。

           3.servlet-config拦截器

             这个拦截器通过各种对象设置到动作必须实现的接口。

           4.fileupload拦截器

             fileupload拦截器将文件和元数据从多重请求转换为常规的请求参数,以便能够将他们像普通参数一样设置到动作上。

            struts的内建拦截器还有很多,比如workflow拦截器,validation拦截器等等,由于篇幅有限这里就不详细介绍了,如果大家有兴趣可以查阅相关资粮,比如struts2 in action 这里介绍的都很详细,只是书翻译的比较烂,下面开始介绍我的自定义拦截器。

自定义拦截器

             在将自定义拦截器之前,让我们先了解一下,怎么将拦截器映射到组件上。可以使用interceptor-ref 元素完成拦截器和动作的关联。

             构建自定义拦截器首先要让自己的类实现一个interceptor接口,实现这个几口要覆写这个类的方法:

             public String intercept(ActionInvocation actioninvocation) throws Exception {}

             如果我们自定义的方法,如果想要设置和覆盖拦截器的参数:

      <interceptor-ref name="authenticationInterceptor" >
                    <param name = "excludeMethods">login,register</param>
                </interceptor-ref>

            就必须继承MethodFilterInterceptor类,我因为这个问题浪费了我好几个小时,才把这个问题解决,具体的拦截器类实现如下:

      @Override
            protected String doIntercept(ActionInvocation actioninvocation)
                  throws Exception {
                Map session = actioninvocation.getInvocationContext().getSession();
                UserDomain user = (UserDomain) session.get("user");
                    if (user == null) {
                        return Action.LOGIN;
                    } else {
                      Action action = (Action) actioninvocation.getAction();
                            if (action instanceof UserAware) {
                                ((UserAware) action).setUser(user);
                        }
                       System.out.println("Logged in: interceptor");
                       return actioninvocation.invoke();
                }
            }

     引入的struts.xml文件如下:
        <interceptors>
            <interceptor name="authenticationInterceptor"
                class="com.duqiao.interceptor.AuthenticationInterceptor" />

            <interceptor-stack name="duqiaoStack">
                <interceptor-ref name="authenticationInterceptor" >
                    <param name = "excludeMethods">login,register</param>
                </interceptor-ref>
                <interceptor-ref name="defaultStack" />
            </interceptor-stack>

        </interceptors>

        <default-interceptor-ref name="duqiaoStack" />
    本文部分内容引自“http://www.blogjava.net/max/archive/2006/12/06/85925.html”。max on java

           

 

           

posted on 2012-10-30 13:03  都督  阅读(5079)  评论(0编辑  收藏  举报