interceptor-使用系统的拦截器

发表时间:2017-05-16 15:43:49 浏览量( 26 ) 留言数( 0 )

学习目标:

1、了解拦截器的概念

2、了解拦截器的作用


学习过程:

一、拦截器interceptor的介绍

拦截器是在action执行之前和之后都会调用,在struts2框架中很多核心功能都是使用拦截器实现的。比如验证、类型转换、防止重复提交、国际化等等都是使用拦截器实现,所以我们在使用action的时候才会显得这么容易。我们看看action的生命周期:

attcontent/d2576703-a361-4d98-9349-8e06f8d84cd3.png

核心Servlet实例化一个ActionProxy和调用execute方法,拦截器拦截请求,在发送给Action之前,和返回的时候都会进行拦截。当Action执行完成之后,请求就会放松一个结果给Result。

二、默认拦截器

我们并没有显示的使用拦截器,我们之前调用的Action又怎么会使用到struts2的拦截器呢。首先,我们得看看我们之前所有的Action的包都会继承struts-default,所以我们首先的研究一下struts-default包,这个包就定义在struts2-core-2.X.X.jar核心包中的struts-default.xml文件中。打开这个文件可以看到在这个包中定义了大量的拦截器。代码如下:

<interceptors>
            <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="cookie" class="org.apache.struts2.interceptor.CookieInterceptor"/>
            <interceptor name="clearSession" class="org.apache.struts2.interceptor.ClearSessionInterceptor" />
            <interceptor name="createSession" class="org.apache.struts2.interceptor.CreateSessionInterceptor" />
            <interceptor name="debugging" class="org.apache.struts2.interceptor.debugging.DebuggingInterceptor" />
            <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="modelDriven" class="com.opensymphony.xwork2.interceptor.ModelDrivenInterceptor"/>
            <interceptor name="scopedModelDriven" class="com.opensymphony.xwork2.interceptor.ScopedModelDrivenInterceptor"/>
            <interceptor name="params" class="com.opensymphony.xwork2.interceptor.ParametersInterceptor"/>
            <interceptor name="actionMappingParams" class="org.apache.struts2.interceptor.ActionMappingParametersInteceptor"/>
            <interceptor name="prepare" class="com.opensymphony.xwork2.interceptor.PrepareInterceptor"/>
            <interceptor name="staticParams" class="com.opensymphony.xwork2.interceptor.StaticParametersInterceptor"/>
            <interceptor name="scope" class="org.apache.struts2.interceptor.ScopeInterceptor"/>
            <interceptor name="servletConfig" class="org.apache.struts2.interceptor.ServletConfigInterceptor"/>
            <interceptor name="timer" class="com.opensymphony.xwork2.interceptor.TimerInterceptor"/>
            <interceptor name="token" class="org.apache.struts2.interceptor.TokenInterceptor"/>
            <interceptor name="tokenSession" class="org.apache.struts2.interceptor.TokenSessionStoreInterceptor"/>
            <interceptor name="validation" class="org.apache.struts2.interceptor.validation.AnnotationValidationInterceptor"/>
            <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" />
            <interceptor name="roles" class="org.apache.struts2.interceptor.RolesInterceptor" />
            <interceptor name="annotationWorkflow" class="com.opensymphony.xwork2.interceptor.annotations.AnnotationWorkflowInterceptor" />
            <interceptor name="multiselect" class="org.apache.struts2.interceptor.MultiselectInterceptor" />

还有一些拦截器栈interceptor-stack

<!-- Basic stack -->
            <interceptor-stack name="basicStack">
                <interceptor-ref name="exception"/>
                <interceptor-ref name="servletConfig"/>
                <interceptor-ref name="prepare"/>
                <interceptor-ref name="checkbox"/>
                <interceptor-ref name="multiselect"/>
                <interceptor-ref name="actionMappingParams"/>
                <interceptor-ref name="params">
                    <param name="excludeParams">dojo\..*,^struts\..*,^session\..*,^request\..*,^application\..*,^servlet(Request|Response)\..*,parameters\...*</param>
                </interceptor-ref>
                <interceptor-ref name="conversionError"/>
            </interceptor-stack>
            <!-- Sample validation and workflow stack -->
            <interceptor-stack name="validationWorkflowStack">
                <interceptor-ref name="basicStack"/>
                <interceptor-ref name="validation"/>
                <interceptor-ref name="workflow"/>
            </interceptor-stack>
            ...下面省略

再继续往下看,可以看到这句代码:

  <default-interceptor-ref name="defaultStack"/>

说明在struts-default包中,这个是默认的拦截器,凡是继承struts-default包的Action都会默认使用这个拦截器。你可以在拦截器栈中找到这个拦截器栈的定义,代码如下:

<interceptor-stack name="defaultStack">
                <interceptor-ref name="exception"/>
                <interceptor-ref name="alias"/>
                <interceptor-ref name="servletConfig"/>
                <interceptor-ref name="i18n"/>
                <interceptor-ref name="prepare"/>
                <interceptor-ref name="chain"/>
                <interceptor-ref name="scopedModelDriven"/>
                <interceptor-ref name="modelDriven"/>
                <interceptor-ref name="fileUpload"/>
                <interceptor-ref name="checkbox"/>
                <interceptor-ref name="multiselect"/>
                <interceptor-ref name="staticParams"/>
                <interceptor-ref name="actionMappingParams"/>
                <interceptor-ref name="params">
                    <param name="excludeParams">dojo\..*,^struts\..*,^session\..*,^request\..*,^application\..*,^servlet(Request|Response)\..*,parameters\...*</param>
                </interceptor-ref>
                <interceptor-ref name="conversionError"/>
                <interceptor-ref name="validation">
                    <param name="excludeMethods">input,back,cancel,browse</param>
                </interceptor-ref>
                <interceptor-ref name="workflow">
                    <param name="excludeMethods">input,back,cancel,browse</param>
                </interceptor-ref>
                <interceptor-ref name="debugging"/>
            </interceptor-stack>

这也就是为什么我们的Action上面都没有配置却可以支持国际化、类型转换和页面数据的绑定等等的功能了。

三、使用struts2定义的一些拦截器

我们也可以在Action中显示的使用系统定义的拦截器,虽然默认这些拦截器并没有使用,我们可以通过这个学习如何在Action的配置文档中配置拦截器。

我们可以在我们之前的添加用户的Action中做出以下修改:

<action name="adduser" class="com.action.UserAction" method="adduser">
<result>/index.jsp</result>
<!-- 引用拦截器 只是局部拦截器, 只对当前的Action起效, 一般都是result之后 -->
<!-- 日志拦截器 -->
<!-- 如果你显示写了拦截器,那么就不会运行默认的拦截器 -->
<interceptor-ref name="logger"></interceptor-ref>
<interceptor-ref name="timer"></interceptor-ref>
<!-- 防止重复提交数据 -->
<interceptor-ref name="token"></interceptor-ref>
<!-- 记得要显示写上默认的拦截器 -->
<interceptor-ref name="defaultStack"></interceptor-ref>
</action>

要显示的使用拦截器只需要使用interceptor-ref 标签的name属性指定拦截器的名称即可。在这里我们添加了logger日志拦截器,timer计算Action执行时间拦截器,还有就是token防止重复提交拦截器。在这里我们需要注意一下几点:

1、当我们在action中显示的引用了拦截器后,就会覆盖默认拦截器,也就是说defaultStack拦截就会失效,原来所有的国际化、类型转换等等功能都没有了。所以我们必须记得要显示的写上默认的拦截器。

2、token拦截的作用是防止重复提交,需要在前台页面加上一个标签:代码如下:

(1)引入struts2的标签:

<%@taglib prefix="s" uri="/struts-tags" %>

(2)在form标准中加入代码:

<s:token></s:token>

(3)如果你重复提交,那么系统会返回一个没有定义result的404错误。所以需要你在action的配置文件中配置result。代码如下:

<result name="invalid.token" type="redirect">/error.jsp</result>