您的位置:首页 > 其它

RIA体系中的设计模式

2006-09-13 11:10 225 查看
前 言

许多开发者都利用设计模式来解决重复性问题。伴随着新技术的涌现,例如RIA,你将有机会构建更加贴近用户需求的应用程序。这样一来,部分描述传统基于服务器的应用程序的模式将会变得更注重客户端的能力。这样的变革会是逐步演进的,幸运的是,现今所用到的技术同样适用这一新模式。这篇文章探究了传统基于服务器的应用程序与RIA模式之间的差别,也阐述了它们共有的高阶设计模式。稍后的文章重点将在特殊的设计模式上,以及如何建立富客户端应用程序。

为什么丰富?

RIA是Web开发和部署模式的一种演变。WWW和HTML最初是用来显示信息和为这些信息进行随机存储的联合体。Web部署模式非常有用,然而,一些开发团队迫不及待地使用HTML来创建应用程序界面。这样一来,由于用户界面控制的有界集,以及缺乏客户端数据控制模式,大部分应用程序在可用性上面是毫无意义的地位。

早期的Web应用程序开发中,围绕着数据传送、资源分配、业务逻辑以及其他基础问题,开发者花费了大量的时间来解决。作为一种成熟和标准的技术来解决这些问题,产生了更有吸引力的Web部署模式。虽然最后已经很成熟,但是表述层还是不完善。RIA的到来帮助开发者有机会实现用户程序界面的功能性需求,创建更实用的应用程序,减少失败的机率,增加交易完成的数量。

丰富的含义有两种,丰富的数据模型和丰富的用户界面。丰富的数据意味着客户端的用户界面能表现和应对更多更复杂的数据模式,这样才能处理客户端的运算以及异步发送、接受数据。优势在于,当页面在服务器上创建完成并交付给HTML后,客户端的程序为用户提供比与服务器交互更良好的感受。为了达到高度复杂的数据模式,客户端允许你构建一个高响应、交互式的应用程序。

丰富也指提供更多的改良界面。HTML只能为用户的界面控制提供有限的功能,反之RIA允许一些富有创造性的界面控制,巧妙的与数据模式相合。传统的互联网模式是线性设计方式,用户唯一的选择就是用批处理方式提交页面到服务器。在这种技术限制下用户体验很糟糕,这种程序不是用户所需要的。连续处理服务器请求和页面更新存在许多障碍,包括页面响应时间、不良的网络带宽、以及满足session或state交叉连接而不断增长的日常开销。伴随着丰富的用户界面,你可以从早期的,服务器响应影响整个界面的运作模式,迁移到只对发出请求的特定区域进行改变的模式上来。本质上,意味着界面将会被分解为由单独个体组成,来适应局部改变、服务器交互、以及客户端内部组件的通讯。

丰富的结果是你可以创建一个客户端界面,这样更容易反映丰富性与复杂性共存的数据和逻辑。

RIA设计

现在企业应用程序一般是分层进行设计,也是根据这个组织程序逻辑的。下面就是典型的N层的应用程序模型:



图1:典型的N层应用程序

这里有3个主要的层:客户层(Client Tier),中间层(Middle Tier)和企业信息系统(Enterprise Information System 简称:EIS)层。每一个主要层根据逻辑的不同又分为几层。
· 客户层包含用户界面和程序接口的容器
· 表示层包含表述内容的逻辑、处理用户会话、状态管理
· 业务层包含系统的业务逻辑
· 综合层包含访问远端程序和数据源的连接器和适配器
· 资源层包含数据库资料以及像ERP这样的企业信息资源和XML文件

一个在J2EE中典型的网络部署系统的结构就如图所示:



图2:典型的Web部署系统

在网络部署系统中,决定程序流程,内容创建和内容传递的逻辑是存在于中间层的,因为传统的Web应用程序的主要特点是一个基于客户端浏览器的请求/响应模型。如果要传递界面,系统需要在它通过中间层向客户层传递之前对内容进行以HTML的形式的格式化和编译。对任何表示层的修改都需要向服务器发出请求,做出响应是整个页面的而不是仅仅做出改动的部分。而在传统的网络模型中采用Applet ,javascript/DHTML等方法来代替客户层的解决方案,始终没有成为主流,这主要是因为各种各样的技术问题,主要是不同浏览器的兼容问题。

富客户模型可以更好的反映出程序的结构,如下图所示:



图3:典型的富客户端模型

不像J2EE程序那样,客户端的请求会导致系统生成一个页面再返回客户端,一个RIA可以支持更小的单元或组件,这些组件从小到一个投票问题到一个完整的视图或界面,富客户模型将界面分解成许多的既可以和用户直接交互又可以和服务器进行通信的小单元模块。

这种将应用程序的设计从以一个个相对独立的页面为中心转移到以组件为中心的转变将会使客户层的设计提升到一个新的层次,并且会使客户层变得更加灵活。富客户层不再成为服务器响应的最终端,这同时也使程序的性能得以提高,用户使用的感觉就好像程序不需要和服务器进行通信或者只是偶尔才需要进行通信。

最后一个RIA模型的特点是事件模型,不像传统的模型那样,服务器收到请求后由上至下的创建客户端界面,你不用预测事件的顺序。既然每个组件都是独立的,就没有必要因为一个请求而做出影响整个视图的反应。要使每个组件都具有向服务器传送信息的能力需要每个组建知道如何处理服务器传递回来的信息。在RIA中,客户端和服务器端交互数据是不同步的,这样你就可以控制组件创建信息发送给服务器和处理服务器的响应,可以为更零散的控制去耦和分离程序功能并且组建面向服务的程序结构。

RIA体系结构中的设计模式

在开发传统Web应用的过程中,企业开发中的设计模式是用来解决代码重用问题的。就如同RIA是从传统Web模型层中演化得来的一样,用来构造RIA的设计模式也是由此演化而来的。这里,名词“模式”用来泛指一个软件开发中解决重复设计问题的通用解决方案。

下一部分描述了如何将功能从传统的前端控制器和商业委托模式转移到新的客户端模式。如同所有的软件设计一样,你会根据需要在合适的场合采用适当的模式。这里描述的高阶模式针对了客户端/服务器通讯中的普遍问题;后面的文章将更加详细的讨论这些客户端模式。

两种软件开发中的普遍问题是:如何与业务逻辑沟通和如何实现客户端与服务器的通讯。建立到业务逻辑的通讯,要求业务逻辑不能和表现层耦合过于紧密,以至于一个改动(不管是逻辑上的还是表现上的)会影响到整个应用。与服务器通讯,需要确保每个请求(Request)包含足够的信息和开销来建立安全、会话、或状态管理。你必须确定每个发送给服务器的消息被认为是一个合法的请求,或者检察消息以获取用于整个应用的标识。

很多种语言实现了传统互联网模式,J2EE环境是其中尤为出色的一种。在Java环境中,你经常使用一个商业委托模式来结构化与业务逻辑的沟通。这个模式的最简单的形式是在真实的业务逻辑外面进行一次封装。这个封装将一个由客户端发来的请求转化为一个对业务逻辑组件的适当请求。为了解决与服务器通讯的问题,很多人采用前端控制器模式。这个模式引导所有请求到一个单一控制器文件,来进行安全性验证并建立正确的控制流,这样它可以在一个HTML页面的表单中做出适当的响应。这两种模式经常一起工作于各种复杂结构下。

除了将一些行为从服务器端转移到客户端外,实现一个RIA体系结构与实现一个传统Web客户端并没有很大区别。从应用设计的角度来看,两个高等级的模式被突出出来:Service Brokering(服务中介)和Client Component to Server Communication(客户端组件到服务器的通讯)。服务中介为单独的组件通讯提供了连接器。在客户端组件到服务器的通讯中,通过提供从组件到服务器的连接性取代了页面级别的连接。针对每个组件,提供适当的应用界面逻辑,包括异步事件处理等等。当然,你也可以根据应用的需要在你的客户端和服务器通讯中建立中心化的通讯结构。

服务中介

一个建立应用的主要原则就是:尽量放松业务逻辑和界面逻辑的耦合程度,这样应用程序界面的变化不会影响到业务逻辑,并且业务逻辑不需要了解它怎么被调用的。如上所述,在传统的环境中,你可以用商业委托模式解决这个问题。在富客户端重你需要考虑到组件和服务两方面的需求。

组件的需求如下:
* 为远程服务提供一个标准的借口。(标准触发方法,设置回调等等)。
* 抽象远程服务层,使它可以是本地的或远程的。
* 抽象调用的方式(SOAP,RMI等等)。
* 当掩护访问或匿名访问时,产生混乱。
* 提供对接受上行请求的组件的操作。
* 提供一个连接到服务的场所。

服务需求包括:
* 抽象调用者。
* 提供标准方法来触发回调事件。
一个符合这些需求的设计包含两个种类的类(Class),如图4所示:



图4:服务中介设计模式

第一个类,服务中介,负责建立到远程服务的适当的途径,并维护一个可用的服务列表以及他们的定义。

第二个类是一个桥接组件,它是一个用户界面组件和服务间的管道。这个桥接组件基于服务定义进行初始化,并了解如何能够与一个本地或远程的服务进行通讯,以及如何通过不同的通讯协议安全的进行通讯,和涉及哪些服务等信息。它包括了对组件的操作,所以它能够在成功,失败或是从服务请求更多的信息时,提供对组件的直接回调方法。



图5: 类之间的关系

为了更深刻的理解这个部分,这里以一个简单的银行应用为例。它包括多个用户选项供用户管理他们的账户以及向银行提出查询。这个应用根据上面提到的层次化模型来构建,用户层提供了一个富应用界面来认证用户,使他们能够察看账户余额和交易记录,以及在账户间转移款项,或记录一个用户服务请求。下一部份将描述如何建立界面,并着重描述如何建立客户端到中间件(中间层次)的通讯。

中间层包括远程服务。在银行案例中,你可以拥有一个位于不同服务器的客户请求服务,因为它紧密结合于一个已存在的客户关系管理系统(CRM)。通讯模式的目标是用来阻止客户端界面了解周围包围的服务的具体情况。事实上,你所需要的全部信息就是服务的标识名称,这样你可以通过服务中介请求一个到该服务的连接。

服务中介从描述如何连接到服务的XML文件中加载应用所知道的所有服务,以及用来引用这些服务的标识名称。当界面提交客户服务请求时,服务中介找到标识的定义并生成连接的必要信息,对界面的其他部分抽象处理的细节。

一个按照这样的组织结构建立的客户端拥有极大的灵活性。例如,你可以增强服务中介,使得它能够察觉服务器和远程请求对本地服务的连接状态,而使得用户界面组件不必知晓应用状态,这样允许你创建偶然连接的应用。

客户端组件到服务器的通讯

在对客户端组件到服务器的通讯进行设计时,必须应用尽可能小并且细粒度的组件来组建界面,并需要具有包含其他组件的能力,同时还要保留它 * 组件功能的中央控制
* 消息接收的中央控制
* 服务通讯的中央控制
* 分离的代码来控制界面逻辑和事件管理
这个设计在用户界面的基础之上建立了四个类,如下图所示:



图6:客户端组件到服务器通讯所需要的四个类

这四个类各自的职责如下:
* 用户界面是控件(日历,数据表格,检查框,颜色等等)依存的地方。
* 视图逻辑包含操作用户界面的代码,映射数据到字段,描绘数据等等。
* 本地数据模型是指那些为应用程序保存数据的组件。
* 控制器和协调器通常被实现为一个组件。

- 控制器负责为用户界面控制所有的过程。它决定如何处理从远程服务器或从用户界面传来的事件。
- 协调器负责从组件到远程服务的外部通讯。协调器还负责承载那些从远程服务回调的方法。

根据这种方式设计用户界面,无论你以何种形式把组件放在界面中,UI组件们都保持了其个体独立性。通过为个别组件提供一个通用的抽象接口,协调器允许UI组件独立运作或是作为一个更大的界面组件的一部分被使用。下图描绘了客户端结构:



图7:客户端体系结构

以银行应用为例,它包含了一个可以把用户服务请求提交到银行的界面组件。服务中介从界面组件中请求一个针对这个远程服务的处理器使得它可以运行适当的方法。这个界面包括大量的控件以及一个按钮来触发响应事件。界面控制器的视图逻辑能够捕捉到该事件。当事件被调用时,它触发控制器并通知视图逻辑来为本次事务建立本地数据模型。等应用程序将数据模型准备好后,控制器通知协调器,让它提交一个用户服务请求并传递所收集的数据。协调器与服务中介联系,请求适当的服务并传递给它一个针对它自己的操作句柄。当协调器受到从服务中介传递来的消息后,它发出一个消息来产生适当的请求。当服务器上的服务运行结束之后,它传递反应数据消息到客户端。桥接器引导这个反应消息到协调器,以决定调用控制器上的哪个方法,并接着调用那条信息来正确的转变界面外观。

永恒的主题

顺理成章,任何应用程序体系结构都渐渐变得脱离它的独特需求,而开始应该遵循一种严格的设计方法。这篇文章提出两种庞大的客户端模式,你应该把它们所阐述的普遍观点应用在所有应用程序开发项目中。稍后的文章会阐述更多的特殊设计模式和它们所能解决的问题。

向丰富迁移

软件开发,以及促使软件开发逐渐向“技术和问题的集合”方向发展的观点是很总要的。Web程序开发的传统模式把信息和程序资源组织起来,来应对广阔的用户需求,但是往往在可用性和用户体验上面很糟糕。RIA在直觉上保留这种Web部署模式,来响应用户体验。这么一来,这种概念就是围绕着怎样构建重视新功能和用户模式的应用程序展开。在观点上会产生微小变化,运用现有的后端服务器和程序结构,也可提供更好的用户体验。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: