JFinal Handler源码解析——从配置到工作原理

今天中午有小伙伴跟我咨询JFinal Handler中的相关姿势,鉴于上次视频中也没有讲清楚,这里特写了一篇博文详细讲解。

##首先我们来看看Handler的配置 在JFinal的Config中可用来配置Handler

@Override
public void configHandler(Handlers me) {
	me.add(new FakeStaticHandler());
}

在这个添加JFinal内置或者我们自己的Handler,在Handlers中有一个ArrayList来存储她们。

final public class Handlers {
	
	private final List<Handler> handlerList = new ArrayList<Handler>();
	
	public Handlers add(Handler handler) {
		if (handler != null)
			handlerList.add(handler);
		return this;
	}
	
	public List<Handler> getHandlerList() {
		return handlerList;
	}
}

下面是Handler的初始化

在项目启动JFinalFilter.init初始化时执行了jfinal.init完成了对整个框架的初始化!我们的Handler也是在这里完成初始化的。

boolean init(JFinalConfig jfinalConfig, ServletContext servletContext) {
	this.servletContext = servletContext;
	this.contextPath = servletContext.getContextPath();
	
	initPathUtil();
	
	Config.configJFinal(jfinalConfig);	// start plugin and init logger factory in this method
	constants = Config.getConstants();
	
	initActionMapping();
	initHandler();
	initRender();
	initOreillyCos();
	initTokenManager();
	
	return true;
}

// 初始化Handler
private void initHandler() {
	Handler actionHandler = new ActionHandler(actionMapping, constants);
	handler = HandlerFactory.getHandler(Config.getHandlers().getHandlerList(), actionHandler);
}

大家再来看看HandlerFactory,在这里从ArrayList的尾部向头部循环,完成对每个Handler中的nextHandler参数赋值。

下面是Handler的结构,她是一个单向的链表。

/**
 * Handler.
 * <p>
 * You can config Handler in JFinalConfig.configHandler() method,
 * Handler can do anything under the jfinal action.
 */
public abstract class Handler {
	
	protected Handler nextHandler;
	
	/**
	 * Handle target
	 * @param target url target of this web http request
	 * @param request HttpServletRequest of this http request
	 * @param response HttpServletRequest of this http request
	 * @param isHandled JFinalFilter will invoke doFilter() method if isHandled[0] == false,
	 * 			it is usually to tell Filter should handle the static resource.
	 */
	public abstract void handle(String target, HttpServletRequest request, HttpServletResponse response, boolean[] isHandled);
}

再来看看HandlerFactory中的getHandler方法。Handler链条的末端是ActionHandler,是专门处理action动态请求的地方。

/**
 * Build handler chain
 */
public static Handler getHandler(List<Handler> handlerList, Handler actionHandler) {
	Handler result = actionHandler;
	
	for (int i=handlerList.size()-1; i>=0; i--) {
		Handler temp = handlerList.get(i);
		temp.nextHandler = result;
		result = temp;
	}
	
	return result;
}

最后我们来看看Handler是怎么工作的

Handler是怎么工作的

上图描述了JFinal中的一个请求的完整过程JFinalFilter->Handler->Action

Handler是怎么工作的

请求到达Handler中之后有三种结局(冥冥中,早已注定我们的三世情缘)

① 直接跳出链条,执行下一个Filter(如果web.xml中有配置)tomcat、jetty容器对静态资源请求处理。

如果都不满足,将返回容器级别的404,可在web.xml中配置404页。*此处的404不受JFinal配置的404页控制。

静态资源进入到ActionHandler时会被直接跳出,执行同上。请求不会到达Action。(示例代码:JFinal/ActionHandler.java)

if (target.indexOf('.') != -1) {
	return ;
}

② 请求已经在Handler完成了该有的使命。在Handler执行了render或者在response中返回了我们想要的数据。

该请求也不会到达Action,这里设置isHandled[0] = true;请求到此为止,也不会去执行后面的Filter。(示例代码:jnode/XmlHandler.java)

if (target.endsWith(".xml")) {
	String view = target.replace(".xml", ".vm");
	RenderFactory.me().getRender("/xml".concat(view)).setContext(request, response).render();
	// 跳出
	isHandled[0] = true;
	return;
}

③ 酒肉穿肠过,佛祖心中留。请求会依次经过各个Handler,抵达Action。

nextHandler.handle(target, request, response, isHandled);

参考

jfinal处理请求的流程问题:http://www.oschina.net/question/1047244_132206

推荐

JFinal2.0极速开发视频教程:http://blog.dreamlu.net/blog/79

如梦技术JFinalQQ交流群:237587118

转载于:https://my.oschina.net/qq596392912/blog/504685

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值