[size=x-large]
最近做日志功能模块,用到拦截器,所以对拦截器的用法稍微了解和总结了一点
关于拦截器及其原理,在这里就不详细讲了。在这里通过代码测试了解几个平时对于拦截器的模糊的地方。
其一:自定义拦截器里面invocation.invoke()返回值到底是什么?
其二:拦截器都是inter1-inter2-inter3-action-inter3-inter2-inter1 模式吗?也就是说,不管怎么样拦截器都会执行action里面的execute方法吗?
其三:调用action里面set方法设值是在哪个环节?
其四:核心调度器ActionInvocation 的作用?
其五:拦截器中可以得到前台的数据吗?[size=x-large][/size]
测试配置文件:
[size]
拦截器类
根据以上结论回答上面提到的问题:
1.拦截器里面的invocation.invoke()方法返回的是一个字符串,该字符串就是你要拦截的action 的execute()方法返回的字符串。
2.拦截器的2种类型:一种是通过调用invoke方法来指定对执行栈的进一步调度执行
另外一种:直接返回一个String类型的ResultCode来终止执行栈的调度执行;例如数据校验的validat拦截器,如果类型发数据校验错误直接不会执行action里面的execute()方法了,而是直接返回input字符串,所以要在配置文件配置结果类型名为input
3.在最后一个拦截器的之后,action执行execute()方法之前。
也就是inter1-inter2-inter3(调用action的set方法开始往里面设值)-action-inter3-inter2-inter1
4:Actioninvocation的操作接口中,有对action/actionProxy,ActionContext/ValueStake 的访问接口,这样当intercepter使用这样一个元素作为参数时,这样interceptor就可以随时与控制流和数据流的元素进行沟通。方便自己对interceptor和action对象构成的执行栈进行逻辑执行调度。
5:可以。当拦截器经过action返回后,在拦截器类中可以通过arg0.getStack().findString("name"))得到前台传来的参数。在经过action之前则得不到。
最近做日志功能模块,用到拦截器,所以对拦截器的用法稍微了解和总结了一点
关于拦截器及其原理,在这里就不详细讲了。在这里通过代码测试了解几个平时对于拦截器的模糊的地方。
其一:自定义拦截器里面invocation.invoke()返回值到底是什么?
其二:拦截器都是inter1-inter2-inter3-action-inter3-inter2-inter1 模式吗?也就是说,不管怎么样拦截器都会执行action里面的execute方法吗?
其三:调用action里面set方法设值是在哪个环节?
其四:核心调度器ActionInvocation 的作用?
其五:拦截器中可以得到前台的数据吗?[size=x-large][/size]
测试配置文件:
[size]
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
<constant name="struts.enable.DynamicMethodInvocation" value="false" />
<constant name="struts.devMode" value="true" />
<package name="default" namespace="/" extends="struts-default">
<interceptors>
<interceptor name = "in1" class = "com.xxg.intercepter.Inter1"></interceptor>
<interceptor name = "in2" class = "com.xxg.intercepter.Inter2"></interceptor>
<interceptor-stack name = "myinter">
<interceptor-ref name = "in1"></interceptor-ref>
<interceptor-ref name = "in2"></interceptor-ref>
<interceptor-ref name="defaultStack"></interceptor-ref>
</interceptor-stack>
</interceptors>
<action name="index" class = "com.xxg.action.LoginAction">
<result name= "dd">
/Test.jsp
</result>
<result name = "input" >
/xxg.jsp
</result>
<interceptor-ref name = "myinter"></interceptor-ref>
</action>
</package>
</struts>
拦截器类
//第一个拦截器
public class Inter1 extends AbstractInterceptor{
@Override
public String intercept(ActionInvocation arg0) throws Exception {
System.out.println("--------before inter1 ------------");
System.out.println("要拦截的Action为------"+arg0.getAction().toString());
System.out.println("在第一个拦截器执行在aciton前,通过值栈得到action中name属性值----"+arg0.getStack().findString("name"));
String result = arg0.invoke();
System.out.println("inter1 resutlt其返回的值-------------"+result);
System.out.println("--------after inter1 ------------");
System.out.println("在第一个拦截器执行在aciton后,通过值栈得到action中name属性值"+arg0.getStack().findString("name"));
return result;
}
}
//第二个拦截器
public class Inter2 extends AbstractInterceptor{
@Override
public String intercept(ActionInvocation arg0) throws Exception {
System.out.println("--------before inter2 ------------");
System.out.println("要拦截的Action为------"+arg0.getAction().toString());
System.out.println("在第一个拦截器执行在aciton前,通过值栈得到action中name属性值----"+arg0.getStack().findString("name"));
String result = arg0.invoke();
System.out.println("inter2 resutlt其返回的值-------------"+result);
System.out.println("--------after inter2 ------------");
System.out.println("在第一个拦截器执行在aciton后,通过值栈得到action中name属性值"+arg0.getStack().findString("name"));
return result;
}
}
//action 类
public class LoginAction extends ActionSupport{
private int id;
private String name;
public int getId() {
return id;
}
public void setId(int id) {
System.out.println("--------action set方法 ------------"+id);
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
System.out.println("--------action set方法 ------------"+name);
this.name = name;
}
public String execute(){
System.out.println("execute invoked!!!");
return "dd";
}
}
------------------------------------------------------
测试结果
--------before inter1 ------------
要拦截的Action为------com.xxg.action.LoginAction@81018b
在第一个拦截器执行在aciton前,通过值栈得到action中name属性值----null
--------before inter2 ------------
要拦截的Action为------com.xxg.action.LoginAction@81018b
在第一个拦截器执行在aciton前,通过值栈得到action中name属性值----null
--------action set方法 ------------22
--------action set方法 ------------erewr
execute invoked!!!
inter2 resutlt其返回的值-------------dd
--------after inter2 ------------
在第一个拦截器执行在aciton后,通过值栈得到action中name属性值----erewr
inter1 resutlt其返回的值-------------dd
--------after inter1 ------------
在第一个拦截器执行在aciton后,通过值栈得到action中name属性值----erewr
[size=medium][/size]
根据以上结论回答上面提到的问题:
1.拦截器里面的invocation.invoke()方法返回的是一个字符串,该字符串就是你要拦截的action 的execute()方法返回的字符串。
2.拦截器的2种类型:一种是通过调用invoke方法来指定对执行栈的进一步调度执行
另外一种:直接返回一个String类型的ResultCode来终止执行栈的调度执行;例如数据校验的validat拦截器,如果类型发数据校验错误直接不会执行action里面的execute()方法了,而是直接返回input字符串,所以要在配置文件配置结果类型名为input
3.在最后一个拦截器的之后,action执行execute()方法之前。
也就是inter1-inter2-inter3(调用action的set方法开始往里面设值)-action-inter3-inter2-inter1
4:Actioninvocation的操作接口中,有对action/actionProxy,ActionContext/ValueStake 的访问接口,这样当intercepter使用这样一个元素作为参数时,这样interceptor就可以随时与控制流和数据流的元素进行沟通。方便自己对interceptor和action对象构成的执行栈进行逻辑执行调度。
5:可以。当拦截器经过action返回后,在拦截器类中可以通过arg0.getStack().findString("name"))得到前台传来的参数。在经过action之前则得不到。