Strut2的工作原理

1、Struts2框架结构
  Struts2的框架结构图如下所示(来自Apache Struts 2 Documentation):
 

  

  图中我们可以看到一个原始请求通过一系列的标准过滤器链传递给Servlet容器,这些过滤器包括ActionContextCleanUp过滤器(可选的,Struts 2.1.3之后的版本均不需要配置该过滤器,下文会对 这个过滤器作进一步解释)还有如SiteMesh等其他过滤器。

   接下来调用核心控制器FilterDispatcher,它将调用ActionMapper去确定该请求将触发哪个action。一旦 ActionMapper确定了调用的action,核心控制器FilterDispatcher会将控制权委托给ActionProxy,由它调用配置 管理器从配置文件中读取配置信息(这些配置信息可以从struts.xml中获取),然后创建ActionInvocation对象,该对象持有拦截器和 对应的Action实例,它将在调用Action之前执行完所有的拦截器。

  当Action返回执行结 果,ActionInvocation将会从struts.xml的配置信息中查找与Action-result-code相匹配的result。接着执 行相应的result,这通常(在有action链的情况下并不会)会触发一些用jsp或者freemarker写的页面模板。其他的一些组件可能会通过 ActionMapper返回相应的URL作为额外的请求。

  在HttpServletResponse返回之前,拦截器会被再次执行(反序调用),最后,响应response通过在web.xml中配置的f过滤器返回给请求者。

ActionContextCleanUp过滤器还是活跃的,核心控制器FilterDispatcher将不清除ActionContext,否则清之。

2ActionContextCleanUp的作用  

  延长action中属性的生命周期,包括自定义属性,以便在jsp页面中进行访问,让actionContextcleanup过滤器来清除属性,不让action自己清除。为了使用WebWork,我们只需要在web.xml配置FilterDispatcher一个过滤器即可。  

  在ActionContextCleanUp中,有这样的代码:

  req.setAttribute(CLEANUP_PRESENT, Boolean.TRUE); 

  如果FilterDispatcher检测到这个属性,就不会清除ActionContext中的内容了,而由ActionContextCleanUp后续的代码来清除,保证了一系列的Filter访问正确的ActionContext.如果用到SiteMesh的Filter或者其他类似Filter,那么设置顺序是: 

 ActionContextCleanUp filter
 SiteMesh filter
 FilterDispatcher

  就是说,一般情况下,如果你要用SiteMesh或者其他过滤器,一般是放在FilterDispatcher或者是现在的StrutsPrepareAndExecuteFilter之前。在调用完所有过滤器的doFilter方法后,核心过滤器FilterDispatcher或者StrutsPrepareAndExecuteFilter会清空ActionContext,如果其他过滤器要一直使用value stack等struts的特性时,如果不用ActionContextCleanUp的话,便得不到想要的值。

     Deprecated. Since Struts 2.1.3, use StrutsPrepareFilter and StrutsExecuteFilter to use other Servlet filters that need access to the ActionContext

3FilterDispatcherStrutsPrepareAndExecuteFilter过滤器

  1FilterDispatcher

  Struts2API文档中显示:Deprecated. Since Struts 2.1.3, use StrutsPrepareAndExecuteFilter instead or

StrutsPrepareFilter and StrutsExecuteFilter if needing using the ActionContextCleanUp filter in addition to this one

  由于该FilteDispatcherr已经Deprecated,这里就不对其作更深的探讨。它的主要功能如下:
  (1)执行Actions
  (2)清除ActionContext
  (3)维护静态内容
  (4)清除request生命周期内的XWorkinterceptors
   另注:该过滤器应该过滤所有的请求URL。一般被设置为/*.

      2StrutsPrepareAndExecuteFilter

FilterDispatcher是struts2.0.x到2.1.2版本的核心过滤器!StrutsPrepareAndExecuteFilter是自2.1.3开始就替代了FilterDispatcher的。

StrutsPrepareAndExecuteFilter与普通的Filter并无区别,方法除继承自Filter外,仅有一个回调方法,有兴趣的可以查看其实现代码。

  StrutsPrepareAndExecuteFilter的prepare与execute,前者表示准备,可以说是指filter中的init方法,即配制的导入;后者表示进行过滤,指doFilter方法,即将request请求,转发给对应的 action去处理。

  StrutsPrepareAndExecuteFilter过滤器中包含相应的功能。
      三个初始化参数:
      1、config参数:指定要加载的配置文件。逗号分割。
      2、actionPackages参数:指定Action类所在的包空间,逗号分割。
      3、configProviders参数:自定义配置文件提供者,需要实现ConfigurationProvider接口类,逗号分割。

 4、ActionContext

   在Struts2开发中,除了将请求参数自动设置到Action的字段中,我们往往也需要在Action里直接获取请求(Request)或会话(Session)的一些信息,甚至需要直接对JavaServlet Http的请求(HttpServletRequest),响应(HttpServletResponse)操作我们需要在Action中取得request请求参数"username"的值:

  ActionContext context = ActionContext.getContext();
  Map params = context.getParameters();
  String username = (String) params.get("username");
  ActionContext(com.opensymphony.xwork.ActionContext)Action执行时的上下文,上下文可以看作是一个容器(其实我们这里的容器就是一个Map而已),它存放的是Action在执行时需要用到的对象一般情况我们的ActionContext都是通过: ActionContext context = (ActionContext) actionContext.get();来获取的.

  我们再来看看这里的actionContext对象的创建:  static ThreadLocal actionContext = new ActionContextThreadLocal();

  ActionContextThreadLocal是实现ThreadLocal的一个内部类.ThreadLocal可以命名为"线程局部变量",它为每一个使用该变量的线程都提供一个变量值的副本,使每一个线程都可以独立地改变自己的副本,而不会和其它线程的副本冲突.这样,我们ActionContext里的属性只会在对应的当前请求线程中可见,从而保证它是线程安全的.

  通过ActionContext取得HttpSession: Map session = ActionContext.getContext().getSession();

 

posted @ 2013-12-26 23:52  mumumy  阅读(343)  评论(0编辑  收藏  举报