JFinal中的aop
jfinal中的aop具体实现就是interceptor
Interceptor初始化
Interceptor的初始化是和actionMapping耦合在一起
Interceptor的创建和全局拦截器的初始化
// 实例化interceptorBuilder ,构造方法无操作
InterceptorBuilder interceptorBuilder = new InterceptorBuilder();
// 将list转为array
Interceptor[] defaultInters = interceptors.getInterceptorArray();
// 将全局拦截器添加到interceptorBuilder私有的拦截器Map中
interceptorBuilder.addToInterceptorsMap(defaultInters);
controller级别的拦截器的初始化
// 创建当前Controller的拦截器,处理@before注解
Interceptor[] controllerInters = interceptorBuilder
.buildControllerInterceptors(controllerClass);
method级别的拦截器的初始化
// 创建当前Method的拦截器,处理@before注解
Interceptor[] methodInters = interceptorBuilder
.buildMethodInterceptors(method);
action的拦截器构建
// 创建此method对应的action的拦截器,此拦截器由全局、controller、method级别的拦截器依次拦截组成的拦截器栈
Interceptor[] actionInters = interceptorBuilder
.buildActionInterceptors(defaultInters,
controllerInters, controllerClass,
methodInters, method);
依次探究buildControllerInterceptors, buildMethodInterceptors, buildActionInterceptors方法的具体实现
/**
* Build interceptors of Controller
*/
Interceptor[] buildControllerInterceptors(Class<? extends Controller> controllerClass) {
// 获取controller类的@before注解
Before before = controllerClass.getAnnotation(Before.class);
// 如果注解不为空,那么创建这个注解对应的拦截器,createInterceptors方法延后分析,否则返回 new Interceptor[0],即NULL_INTERCEPTOR_ARRAY;
return before != null ? createInterceptors(before) : NULL_INTERCEPTOR_ARRAY;
}
/**
* Build interceptors of Method
*/
Interceptor[] buildMethodInterceptors(Method method) {
// 获取method的@before注解
Before before = method.getAnnotation(Before.class);
// 如果注解不为空,那么创建这个注解对应的拦截器,createInterceptors方法延后分析,否则返回 new Interceptor[0],即NULL_INTERCEPTOR_ARRAY;
return before != null ? createInterceptors(before) : NULL_INTERCEPTOR_ARRAY;
}
/**
* Build interceptors of Action
*/
Interceptor[] buildActionInterceptors(Interceptor[] defaultInters, Interceptor[] controllerInters, Class<? extends Controller> controllerClass, Interceptor[] methodInters, Method method) {
// 获取清理拦截器级别,并清理上层拦截器
ClearLayer controllerClearType = getControllerClearType(controllerClass);
if (controllerClearType != null) {
defaultInters = NULL_INTERCEPTOR_ARRAY;
}
ClearLayer methodClearType = getMethodClearType(method);
if (methodClearType != null) {
controllerInters = NULL_INTERCEPTOR_ARRAY;
if (methodClearType == ClearLayer.ALL) {
defaultInters = NULL_INTERCEPTOR_ARRAY;
}
}
// 按照全局,controller,method级别依次添加到action的拦截器栈中
int size = defaultInters.length + controllerInters.length + methodInters.length;
Interceptor[] result = (size == 0 ? NULL_INTERCEPTOR_ARRAY : new Interceptor[size]);
int index = 0;
for (int i=0; i<defaultInters.length; i++) {
result[index++] = defaultInters[i];
}
for (int i=0; i<controllerInters.length; i++) {
result[index++] = controllerInters[i];
}
for (int i=0; i<methodInters.length; i++) {
result[index++] = methodInters[i];
}
return result;
}
createInterceptors(before)方法解析
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Before {
Class<? extends Interceptor>[] value();
}
Before注解的定义,表明before注解是支持同时配置多个interceptor的
private Interceptor[] createInterceptors(Before beforeAnnotation) {
Interceptor[] result = null;
@SuppressWarnings("unchecked")
// 获取参数中拦截器的Class
Class<Interceptor>[] interceptorClasses = (Class<Interceptor>[]) beforeAnnotation.value();
if (interceptorClasses != null && interceptorClasses.length > 0) {
// 创建interceptor承载数组
result = new Interceptor[interceptorClasses.length];
for (int i=0; i<result.length; i++) {
// 保证每个拦截器的实例只有一个,如果拦截器缓存中有目标拦截器,就直接取出
result[i] = intersMap.get(interceptorClasses[i]);
if (result[i] != null)
continue;
// 新建拦截器,并添加到缓存Map中
try {
result[i] = (Interceptor)interceptorClasses[i].newInstance();
intersMap.put(interceptorClasses[i], result[i]);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}
return result;
}
由创建interceptor实例可知,实际上特定interceptor在jfinal app中实际上只有一个,此举可有效解决为每个action配置拦截器时新建interceptor的资源消耗,但同时不免有线程安全问题
getControllerClearType(controllerClass), getMethodClearType(method);分析
private ClearLayer getMethodClearType(Method method) {
// 处理ClearInterceptor注解
ClearInterceptor clearInterceptor = method.getAnnotation(ClearInterceptor.class);
// 如果clearInterceptor!=null,则取到注解中传递的value
return clearInterceptor != null ? clearInterceptor.value() : null ;
}
private ClearLayer getControllerClearType(Class<? extends Controller> controllerClass) {
// 处理ClearInterceptor注解
ClearInterceptor clearInterceptor = controllerClass.getAnnotation(ClearInterceptor.class);
// 如果clearInterceptor!=null,则取到注解中传递的value
return clearInterceptor != null ? clearInterceptor.value() : null ;
}
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface ClearInterceptor {
ClearLayer value() default ClearLayer.UPPER;
}
public enum ClearLayer {
/**
* clear the interceptor of upper layer
*/
UPPER,
/**
* clear the interceptor of all layers
*/
ALL;
}
可能某些action不需要在其上层的controller、全局级别的拦截,此时,作者引入了清理某个级别拦截器的注解,可以方便的清理某个action上的某个层次的拦截器,但同时如果开发者只是希望移除某个级别之上的某个拦截器,则比较难以处理,按照jfinal的处理逻辑,只能先移除某个级别的所有拦截器,然后再添加需要的拦截器,不免有些麻烦,不知作者后期是否会对这种情况提供支持。
interceptor运行时
在jfinal的运行时中已经分析过了
小结
解读JFinal中的interceptor组件的实现,servlet规范中的filter,struts2中的拦截器,以及springmvc中的拦截器,这些都说明在web开发中拦截器的不可缺少性,在url拦截,全县处理,日志记录等方面可以无侵入性的提供功能实现。