struts跳转到ftl页面处理流程
基本上,struts的绝大部份功能是用拦截器提供,所以用这个词去回答可以命中90%的问题,而不幸的是, 这个功能是DefaultActionInvocation处理的, 并且它是最基本必不可少的功能, 所以, 它刚好没做为一个拦截器实现.?
struts在处理这块的工作流程是这样的:?
1. 转向ftl页面时, struts的DefaultActionInvocation发现你的result是ftl的,它将调用FreemarkerResult来处理.?
2. FreemarkerResult将调用FreemarkerManager来创建ftl要用的TemplateModel, 在这个templateModel中就包含了struts的所有tag?
3. 接着, FreemarkerResult调用ftl的template.process(templateModel, output)方法解析和输出结果?
这个机制的本质是来自freemarker的这个特性:?
http://freemarker.org/docs/ref_directive_userDefined.html#ref.directive.userDefined?
另外, 你提到为什么不用asign, 本质上来说, asign的最终原理也是这么一个处理过程, 只是这个templateModel的初始化给显式的放在了ftl页面中(做初始化的instance是在servlet中准备)?
其原理是: 你配置的FreemarkerServlet会在ftl的templateModel(或者enviroment)中放入一Map变量JspTaglibs, 因为JspTaglibs['xxx.tld']会转成map.get('xxx.tld')的方法调用,然后,JspTaglibs的实现类TaglibFactory, 就有机会去解析传入的xxx.tld, 并将这些tag导入到templateModel.?
所以, 从最后的效果来看, Freemarker能借助这个普通的assign语法, 实现了对tag的引用