第1章 Struts 2: 现代Web框架
本章内容
- [ ] 构建Web应用程序
- [ ] 使用Web框架
- [ ] 探索Struts2框架
- [ ] 介绍拦截器(interceptor)和ValueStack
1.1 Web应用程序:快速学习
relationship-servlet-web
- 一个Servlet容器里可以包含一个或多个Web应用程序
- Servlet API提供会话机制,可以关联来自于一个给定客户的请求组
Web应用程序处理请求时都必须要解决:
- 请求参数到Java类型的数据绑定
- 验证数据
- 访问业务逻辑
- 访问数据库
- 呈现表示层(HTML等)
- 提供国际化和本地化的支持
1.2 Web应用程序框架
框架是一种结构化的软件。
框架主要从两个方面帮助我们快速开发:
- 尽量自动化Web应用程序开发过程中的常见问题
- 尽量提供优秀的架构解决方案来优化Web应用程序中常见的工作流
Web应用程序 : 是一种结构化的软件,它提供了该领域中常见的任务的自动化实现,同时作为一个内置的架构解决方案可以被在其上实现的应用程序轻松地继承。
1. 框架自动化了常见任务 不要“重新发明车轮”。好的框架提供了透明(即使不透明也会很优雅)的机制来将开发人员从法索的任务中解放出来。
2. 框架提供了架构解决方案 框架的结构来源于内建的接口、类对工作流的抽象。作为一个面向动作的框架,Struts2结构核心的关键抽象是动作。
自己开发框架的两个突出问题:
- 新开发人员总是必须从基础学习这个框架
- 内部框架不能跟上行业的步伐持续地修订,时间长了内部框架会遭受架构的侵蚀,并且会生硬地接纳很多扩展
1.3 Struts 2框架
Apache Struts 2是一个全新的非常先进的Web应用程序框架,它不只是原来Struts 1框架的一个新版本,它基于OpenSymphony WebWork框架,是一个全新的框架。
Struts 2简史
Struts 2是实现MVC设计模式的第二代Web应用程序框架。第一代Struts框架的主要目的是把MVC模式从桌面应用程序引入Web应用程序。这个合成的模式偶尔也被成为Model 2模式。
Struts 2新特性:
- 用来从动作逻辑中分层出横切关注点的拦截器
- 为了减少或者消除XML配置基于注解(annotation)的配置方式
- 一个贯穿整个框架的强大的表达式语言OGNL(Object-Graph Navigation Language)的标签API
Struts 2 概览:MVC模式 MVC设计模式与Struts的实现:
MVC | Struts |
---|---|
模型(model) | 动作(action) |
视图(view) | 结果(result) |
控制器(control) | 过滤分配器(FilterDispatcher) |
struts2-mvc-workflow
Struts 2 MVC通过3各核心框架组件实现:动作、结果和FilterDispatcher
1.控制器——FilterDispatcher
控制器的角色是由Struts 2的FilterDispatcher来扮演的。这个重要的对象是一个Servlet过滤器,它检查每一个传入请求,决定哪个Struts 2动作处理这个请求。框架帮助你完成所有控制器的任务。你只需要告诉框架哪个请求URL需要映射到哪个动作即可。可以通过基于XML的配置文件或者Java注解来完成任务。
说明
Struts 2朝着零配置(zero-configuration)的Web应用程序进行了长期的探索与研究。零配置的目的在于从约定而不是配置得到应用程序的元数据,例如哪个URL映射到哪个动作。在零配置的模式中,Java注解起到了重要的作用。尽管零配置还没有完全实现,但现在你可以使用Java注解和约定来大幅度地减少基于XML的配置文件。
2.模型——动作 Struts 2的动作组件有两个作用:
- 一个动作将业务逻辑调用封装到一个单独的工作单元中
- 动作是一个数据传输的场所
3.视图——结果
视图是MVC模式的呈现组件。他们通常是JSP页面、Velocity模板或者用其他表示层技术呈现的页面。 视图的作用:将应用程序的状态转换为一种用户可以与之交互的可视化的表示。
Struts 2的工作原理 Struts 2提供了一个更整洁的MVC实现,这些整洁的线条依赖于其他几个参与每一个请求处理的关键架构组件的帮助,主要包括:
- 拦截器
- OGNL
- ValueStack
struts2-work-princeple
Struts 2请求处理使用在动作和结果之前或之后调用的拦截器
上图引入了新的Struts 2组件:ActionContext、拦截器、ValueStack和OGNL。
1. 拦截器
- 每一个动作都有一组拦截器与之相关联
- 拦截器在动作执行之前、之后都被调用,并且在结果执行完毕后才被触发
- 不一定两次触发都做工作
- 允许常见的、横切的任务在简介、可重用的组件中定义,从而能够和动作的代码分离
说明
**拦截器**是一种可以在请求处理之前或者之后执行的Struts 2组件。它提供了一种在其中定义不同的工作流和横切任务的架构组件,以便能够简单地重用这些组件,并且能够与其他架构关注点分离。
使用自定义的拦截器可以完美地解决很多任务。
2. ValueStack和OGNL
ValueStack是保存与请求处理相关的所有数据的一个存储区域。可以将其当做一个便签,Struts 2将所有相关的数据集中保存在ValueStack中。
定义
Struts 2使用ValueStack作为请求处理过程中所需的应用程序域数据的***存储区域***。数据被放入ValueStack为请求处理作准备。在动作执行过程中,数据在这里被操作。当结果呈现到响应页面时,数据从这里被读取。
OGNL是一种访问存储在中心存储库(repository)中数据的工具。更准确地说,它是一个允许你引用或者操作ValueStack中的数据的表达式语言.
定义
OGNL是一个用来引用、操作ValueStack中数据的强大的表达式语言(还不止于此)。
ValueStack和OGNL微妙和强大的地方是它们不属于框架中任何独立的组件。拦截器和结果都可以使用OGNL表达式语言来指向ValueStack中的值,ValueStack中的数据跟着处理请求经过所有阶段,它贯穿框架的整个过程。之所以能做到这点是因为ValueStack存储在一个线程本地对象(ThreadLocal)中,它的名字叫ActionContext。
ActionContext包含所有的数据,这些数据构成了动作执行的环境。它包含ValueStack,也包含框架会使用的内部数据,如:请求对象、会话对象以及从Servlet API中得来的应用程序映射。
使用ThreadLocal可以在相同线程执行中的任何地方访问ActionContext或者ValueStack。因为Struts 2每一个请求的处理都发生在一个单独的线程中,所以可以在框架处理请求的任何一个地方访问ValueStack。
在框架里的多个地方都使用OGNL来引用、操作ValueStack中的数据。
第2章 初始Struts 2
本章内容
- [ ] 声明应用程序的架构
- [ ] 部署Hello World应用程序
- [ ] 构建基于XML的应用程序
- [ ] 使用Struts注解
2.1 声明性架构
配置(Configuration):声明应用程序的Struts2组件的行为成为配置。
如下两种配置非常重要:
- 配置框架:接近于管理活动。默认情况下,Struts 2查找以.action结尾的URL,但是你可以配置框架查找.do(Struts 1的默认扩展名),甚至可以不适用任何扩展名。
- 声明应用程序的架构:这类型的配置更重要,我们称之为声明性架构,包括定义应用程序使用的Struts 2组件,以及将它们连接起来形成需要的工作流程路径(workflow path)。这里说的工作流路径是指当一个特定的URL呗单击时会触发哪个动作,以及该动作会选择哪个结果来完成处理流程。
定义
声明性结构是一种特殊的配置方式,它允许开发人员以描述而不是硬编码干预的方式创建应用程序的架构。开发人员使用高级工件(artifact)来描述架构组件,例如,XML文件或者Java注解,系统会利用这些高级工件创建程序的运行时实例。
开发人员只需要声明哪些对象作为应用程序的动作(action)、结果(result)以及拦截器(interceptor)。这个声明过程主要包括指定哪些Java类实现哪些接口。通常情况下,开发人员只需要实现动作,之后将它们与内建的结果和拦截器关联起来即可。
声明架构的两种方式:
- 通过XML方式
...
<action name="Login" class="manning.Login">
<result>/AccountPage.jsp</result>
<result name="input">/Login.jsp</result>
</action>
<action name="Registration">
<result>/Registration.jsp</result>
</action
<action name="Register" class="manning.Register">
<result>/RegistrationSuccess.jsp</result>
<result name="input">/Registration.jsp</result>
</action>
...
框架使用一个专门的文件作为这个大描述文件的入口点,这个入口点文件就是struts.xml文件。这个文件驻留在Java类路径(classpath)下,并且必须由开发人员创建。虽然可以在struts.xml文件中声明所有的组件,但是为了应用程序模块化,开发人员通常只用这个文件包含次级的XML文件。
- 通过Java注解方式
@Results({
@Result(name="input",value="/RegistrationSuccess.jsp"),
@Result(value="/RegistrationSuccess.jsp")
})
public class Login implements Action {
public String execute() {
// Business logic for login
}
}
定义
智能默认提供了内建的组件,在不需要开发人员更多配置的情况下,就可以解决常见的领域工作流,从而允许以最小的开发工作量实现常见的应用程序功能。
这些预先定义的组件是Struts 2智能默认值的一部人。如果你感兴趣,struts-default.xml中声明了很多这样的组件,这些文件在struts2-core.jar中。