第
3 部分: 服务实现
本系列五篇文章的第三篇解释了服务是怎样实施的。服务实现从决定由哪个参与者提供服务、哪些用户将要使用这些服务开始。这个决定对于服务可用性、分布情况、安全性、交易范围及耦合来说,具有十分重大的意义。在作出这些决定之后,您可以对怎样实施每一项服务功能性性能,以及使用需要的服务进行建模。然后您可以使用
IBM? Rational? Software Architect 中包含的 UML-to-SOA 转换特性,以创建一个可以在
IBM? WebSphere? Integration Developer 中使用的 Web 服务实施方案,从而进行服务的实施、测试和部署所完成的解决方案。
本文的写作背景
对 SOA 建模的完整理解,需要知道提供商具体是如何实施一项服务,以及消费者具体是如何使用此项服务的。如果实施方案实施起来很困难,那么有可能是因为服务规范是不合适的,或者是识别了错误的服务。本文向您展示了怎样设计我们在前面文章中开发的每一项服务的实施接口。实施方案的设计由三个步骤组成:
1.决定由哪一个服务提供商提供哪一项服务。
2.设计服务的实施方案。
3.组合并连结在建模一个完整的实施方案中所涉及到的所有服务消费者与提供商。
决定由哪一个提供商提供什么服务(不止一个提供商),由许多的因素决定,包括:
功能性的聚合以尽可能地实现重用
服务最有可能被使用的地方
服务最有可能被部署到的地方
需要什么质量的服务
功能性区域的稳定性
预期最有可能发生变更的地方
域中能够容忍多大程度的耦合
降低耦合情况以降低变更所能产生的影响
安全性问题
合适的平台实施方案技术
对已有系统的集成与重用
所有这些关注点的具体分析,已经超出了本文的讨论范围,但是在 IBM? SOMA 方法中却进行了详细地讨论。这里,我们在一定程度上假设,IT
架构师会决定由哪一个参与者提供什么服务,这样我们就可以只关注于如何对提供商进行建模,以及怎样将它们组合到消费者方案中。
注意:
面向服务的架构建模语言(SoaML)标准使用术语参与者,而且不区分服务提供商与服务消费者。这是因为,通常意义上,参与者即会提供服务又会使用服务。从参与者的服务和请求端口来看,可以很清楚地看到实际上提供了什么以及使用了什么,使得进一步识别参与者变得不太必要。
对于本系列的所有文章,我们将会使用现有的 IBM? Rational? 工具,来构建方案工件,并将其联系在一起,这样我们就可以根据需求确认方案,并且更加有效地管理变更。另外,我们通过将
Object Management Group(OMG)SoaML Profile 添加到 IBM? Rational?
Software Architect 中的 UML 模型里,来扩展统一建模语言(UML)以进行服务建模。表
1 提供了总体流程的概况,我们将会在开发本文范例的过程中使用这一流程与相应的工具来构建工件。
表 1. 开发进程角色、任务与工具
服务识别与规范评审
让我们从评审在前面文章中识别和指定的服务规范开始。图 1 显示了揭示处理购买订单所需功能的服务接口。
图 1. 处理购买订单的功能
显示揭示的功能
图 2 显示了完整的 Scheduling 服务接口。该服务接口是一个简单的接口,因为对于使用日程安排服务来说,并没有感兴趣的协议。
图 2. Scheduling 服务接口
Scheduling ServiceInterface
的类图
图 3 显示了 ShippingService 服务规范。
图 3. Shipping 服务接口
ShippingService ServiceInterface
的图
该服务接口有一点点复杂,因为通过使用一个简单的回叫形式的交互,它为传递者及订购者之间的交互进行了建模。因为这种指定包含了一个协议,我们使用一个定义服务协议中会涉及到的角色(属性)的服务接口来建模。这些角色的责任是由它们的类型定义的,它就是服务接口提供或者需要的接口。ShippingService
服务拥有的 shippingService 交互定义了传递者与订购者之间进行的交互。这种交互将会成为联系该服务接口定义的服务的服务渠道的协议。
图 4 显示了 InvoicingService 服务规范。
图 4. InvoicingService 接口
ShippingService ServiceInterface
的图
该协议同样有一些复杂,因为提供的和需要的服务功能性性能必须得到调用,并对应于特定的顺序。在这种情况下,可以使用一种活动来定义协议。
图 5 显示了 Purchasing 服务规范。
图 5. Purchasing 服务接口
Purchasing ServiceInterface
的图
Purchasing 服务接口代表了在原始 Process Purchase Order 业务过程中指定的功能性性能。它代表了识别的和设计的服务,以实现业务过程。因为没有与该规范相联系的协议,我们使用一个简单的接口,再一次对其建模。
现在我们就可以设计工件了,该工件提供了每一种服务,并实现了揭示的功能。
服务的实现
所谓的服务定义了一系列的能够满足服务消费者或者用户需要的功能。服务实施方案设计的第一步,是划分服务。这就是说,我们必须想好我们将会提供什么服务,哪一个服务提供商会提供什么样的服务功能。这是设计一个
SOA 非常关键的一部分,因为选择提供商将会建立服务消费者与提供商之间的关系。因此,这就建立了一个系统以及系统各部分之间潜在耦合关系的功能。
您可以将所有的操作都放到一个单独的服务中,并因此拥有一个简单的解决方案。但是同时所有的客户都会依赖于一个服务,这就造成了很高的耦合度。提供商方面很小的一个变更,都有可能会造成所有消费者也都会产生变更。就这就是过去
C 编程时代模块化最常面临的问题。您也许会说,可以为每一个功能性性能都创建一个单独的服务,但是这将会导致产生一个复杂的系统,该系统在内聚度和封装性上面的表现十分糟糕。在消费者与提供商之间进行模块化交互可能是十分困难的,这种交互遵循一种交互协议使用一系列相关的功能性性能。
于是,决定服务的参与者是一种需要技巧的工作,并且通常会受到大量折中考虑的影响。其中分布性会发挥十分关键性的作用。如果我们可以设计不受参与者位置影响的
SOA 方案的话,那还不错,但是通常来说这是不现实的。服务部署的位置,会是消费者及其他需要服务的群体所在的地方,它对方案的性能、可用性及安全性方面会有重大意义的影响。在方案架构中忽略这一点,在方案的可执行性方面会造成十分严重的后果。
我们在这里面临的问题是十分简单的,所以初始 Business Process Modeling Notation(BPMN)业务过程概述中的汇于泳道,对于哪些参与者将会提供服务,哪些将会消费服务,都给出了一个明确的线索。图
1 中的所有服务及该图下面具体的服务规范,为所有的服务提供了服务提供商的模型。这是一个十分简单的例子,其中有多个参与者只会提供一种服务,并且只有一种功能。这与实际情况是不相符的。参与者通常会提供或者消费(或者即提供又消费)多种拥有多种功能性性能的服务,在这里,我们故意把这个例子简化,使之抽象出具体复杂的情况以便您更好地理解其中的概念。
注意:
本文中提到的服务实现化问题的概念,与在 SOMA 中描述的有些出入。在 SOMA 中,服务实现处理的是架构性决策问题,它关注的是方案的模板与模式、SOA
引用架构的具体内容、技术上的可实现性以及原型问题。这超出了本系列文章的讨论范围,本文只涉及到了决定由哪些参与者提供服务、哪些参与者消费服务,以及怎样决定这些内容。
结账
一个结账者为计算一个购买订单的初始价值提供了 Invoicing 服务。然后当他得知传递信息之后,可以进一步地完善估价活动。初始价值估计可以用于确认客户拥有相应的支付能力和信用,或者一直想要购买产品。在完成整个订单之前就进行确认会更好。
在开始这个服务时,我们创建一个定义其需求的系统用例,以及一个叫做 Invoicer 实现用例的参与者,如图
6 所示。Invoicer 参与者将会位于信用包中,并导入 CRM(客户关系管理)包,以使用公共的服务数据(信息类型)定义。
图 6. 最初的 Invoicer 服务提供商
显示 Invoicer Participant
的图
Invoicer 参与者提供了 InvoicingService 服务。我们通过向 Invoicer 添加
Service 来对其建模,它是 InvoiceService 服务接口类型的。所有的服务是由服务接口输入的,该服务接口定义了什么功能性性能是提供的,什么是需求的,以及使用它们的协议。图
7 显示了 Invoicer 与添加的结账服务。
图 7. 对 Invoicer 服务提供商添加 InvoicingService
向 Invoicer 添加结账服务
我们可以通过服务的类型来知道该服务提供了 Invoicing 接口,并且需要使用 InvoiceProcessing
接口。从服务的类型中,我们可以知道与服务相关消费者使用服务所需要执行的操作,以及 Invoicer(或者其他的提供商)实施时必须执行的操作。服务的任意使用和实施必须与服务的规范及其协议相一致。
Invoicer 提供了 Invoicing 接口,它涉及到了两种操作:
initiatePriceCalculation
completePriceCalculation
Invoicer 必须为每一种指定如何提供操作的服务操作提供一种设计。当价值估算按照服务协议中指定的那样完成时,方法必须调用
InvoiceProcessing 接口的 processInvoice 操作。如图 8 所示,Invoicer
构件拥有两个与提供操作名字相同的行为。
图 8. Invoicer 服务实施
服务操作实施图
completePriceCalculation 活动是 Invoicing::completePriceCalculation
服务操作的方法。它使用一种模糊行为,来估计总体的价值,然后它会激活结账端口上的 InvoiceProcessing::processInvoice
操作。(processInvoice 操作的目标输入帧是结账服务端口,如包含操作的活动分区所示)。注意这与
InvoicingService 服务接口指定的结账协议相一致。
initiatePriceCalculation 模糊行为是 initiatePricesCalculation
服务操作的方法。该操作通过使用自然语言或者在模糊行为主体中获取的 Java 代码来实施。
产品日程安排
一个产品日程安排参与者会提供 Scheduling 服务,以决定在什么地方生产货物以及什么时候生产。可以使用该信息来创建一个使用的传递日程安排以处理购买订单。
产品参与者通过它的日程服务端口来提供 Scheduling 服务接口,如图 9 所示。
图 9. Productions 服务提供商
Productions Participant
的图
服务操作方法是 requestProductionsScheduling 及 sendShippingSchedule
行为。这些实施方案的具体内容并没有显示在图表中,并有可能由开发员使用一些更加实用、特定平台的语言来实施。
传递
一个传递服务提供商会为一个客户提供 Shipping 服务接口以传递货物。它还需要 ScheduleProcessing
接口,以请求客户处理完整的日程安排。图 10 显示了 ShippingService 服务接口来提供传递服务。
图 10. Shipper 服务提供商
Shipper 规范与实施
在本事例中,我们将 Shipper 参与者的指定与它的实现分隔开来。该指定参与者无论是在内部还是外部,都为实现参与者描述了架构。我们这样做是因为可能会有
Shipper 参与者指定的许多种不同实现方法,每一种方法都有不同的附加的功能及需要及服务的质量。我们展示了一个实现的参与者,ShipperImpl。特别是对集合的服务,我们将会使用
Shipper 参与者,而不是直接地引用 ShipperImpl。然后,在部署和运行的时候,该规范可以替换成各种的实施方法,以获得服务所需的质量。
后续的内容
现在我们已经完成了满足业务目标所需要的服务参与者的识别、指定以及执行(或者实现。结果是服务方案架构的技术中心设计模型。但是我们仍然没有创建一个服务参与者,该参与者集合了
Invoicer、Productions 及 Shipper 提供的服务,并使用它们来处理一个购买订单。本系列五篇文章的第四部分,“使用面向服务体系架构建模语言(SoaML)建模,第
4 部分:服务组合”,显示了怎样集合和联系这些服务提供商,以为业务需求提供一个完整的方案。
第 4 部分: 服务组合
本文的写作背景
在本文中,我们组合了以前所创建的服务参与者,在第三篇中,我们使用其他参与者的功能。这就是说,我们将会从其他的服务的组合或者组合当中创建一个新的服务。这种服务组合的技术可以重复地使用无限次,不管您的关注点是什么,也不管抽象的层次如何。但是,可能会有结构上的限制因素,影响到服务操作、安全和性能关注、数据交换容量、线性层次交互协议和绑定问题的整体性,它们可能会限制什么构件提供什么服务。这个问题决定了方案的结构,并超出了本文的讨论范围。但是您可以查看
IBM? developerWorks? 名为“使用一个引用结构来设计一个 SOA 方案”的文章以得到这个重要话题的具体信息。
本系列所有的文章有一个共同点,那就是我们使用已存在的 IBM? Rational? 工具来构建方案工件并将它们再一次联系起来,这样我们就可以根据需求确认方案的可执行性,并更加有效地管理变更。另外,我们通过向
IBM Rational Software Architect 中的 UML 模型添加对象管理组面向服务架构建模语言(OMG
SoaML)概述,来为服务建模扩展统一建模语言(UML)。表 1 提供了一个总结,关于我们在开发范例时使用的总体进程,以及用于构建工件的工具。
表 1. 开发进程角色、任务与工具
服务实现审核
让我们从评审前面文章中执行的服务参与者开始讨论。图 1 显示了 Invoicer 服务提供商。
图 1. Invoicer 服务执行
服务操作实现图
Invoicer 服务参与者为计算购买订单的初始价值提供了结账服务,并在知道传递信息时改进所做的估价。订单的全额价值取决于产品是在哪里生产的,以及从哪里进行传递的。初始价值计算可能用于确认消费者拥有足够的信用,或者仍然想要购买产品。在完成订单之前最好确认这一点。
图 2 显示了 Productions 服务提供商。
图 2. 产品服务提供商
Productions 参与者图
Productions 服务参与者提供了一个日程安排服务,以决定在哪里生产一种商品以及什么时候生产。该信息可以用以创建处理购买订单所使用的传递日程安排。
图 3 显示了 Shipper 服务提供商。
图 3. Shipper 服务提供商
传递者规格与执行图
Shipper 服务提供商为一个完整的订单向客户提供了传递商品的服务。该服务需要 ScheduleProcessing
界面以请求完成日程安排的消费者进程。
服务组合
现在一些提供商已经提供了所有的服务,所以我们可以开始使用组合中的这些提供商以满足原始的业务需求了。该组合根据业务需求来组合服务,以为
Purchasing 服务提供了一种方法。我们将会创建一个 OrderProcessor 参与者,该参与者提供了一种购买服务以处理购买订单。然后我们会创建一个
Manufacturer 参与者,它组合了 Invoicer、Productions、 Shipper
参与者以及 OrderProcessor 构件的实例,以执行服务操作进而处理购买订单。
订单处理参与者
购买订单处理服务是由 Purchasing 服务界面指定的(如图 4 所示),它包括了以下的功能(或者操作):
+ processPurchaseOrder (customerInfo
: Customer, purchaseOrder : PurchaseOrder) : Invoice
这种服务是由 OrderProcessor 参与者提供的。OrderProcessor 是这样一种参与者,它通过将服务提供商联系在一起来提供一种服务,这些提供商根据一个服务协议来进行组织。这就是说,有一些所提供服务的方法被设计成以一种特定的方式来使用其他的方法。这个构件通过它的购买服务端口来提供
Purchasing 界面。所有的客户之间的交互都是通过这个端口进行的,因此将客户与构件可能与其他服务客户或者提供商之间的交互隔离开来。这种模型之中限制的耦合,使得当市场和服务消费者及提供商发生变更时,变更起来更加容易。
图 4. Purchasing 服务界面
Purchasing ServiceInterface
图
OrderProcessor 构件的组织就显示在如图 5 所示的 Project Explorer 视图中。
图 5. 订单管理业务功能性区域(包)
Project Explorer 视图显示了
OrderProcessor
OrderProcessor 参与者包含在 org::ordermanagement 包中,它用于组织与订单管理相关的服务。订单管理包还包含了相关的服务界面和其他的参与者。
图 6 所示的 OrderProcessor 图提供了一个关于 OrderProcessor 服务提供商的外部视图及其服务和请求报告。所需要的服务被标记成
Requests 以将参与者与功能区分开来。外部的或者黑箱视图就是其他参与者所看到的内容。接下来例子中显示的参与者的内部结构,提供了结构的内部或者黑箱视图,以支持参与者的执行设计。
图 6. OrderProcessor
OrderProcessor 参与者图
外部视图并不是与实现相隔离的规格;它只是构建一些方面的简单视图。如果架构师或者开发员想要完整地将服务提供商的规格与它可能的实现分隔开来,那么应该使用一个规格构件,就像在
图 3 中对 Shipper 参与者所做的那样。一个规格构件定义了服务消费者与服务提供商之间的契约。规格参与者可以由许多具体的构件来实现,这些构件以一种可以实现契约并提供可靠服务质量的方式来提供服务。您可以查看“第
2 部分:服务实现”以得到更多的具体信息。
OrderProcessor 参与者非常的简单和稳定。因此,在这个例子中,架构师或者开发员并不想要使用一种服务规格。结果,任何使用
OrderProcessor 构件的服务消费者都需要进行这种特定的执行。它是否是一种可用的设计,取决于服务将会被使用多少,以及它随着时间将会发生什么样的变化,只有业务或者方案架构师可以决定特定的系统可以承受多大程度的耦合度。
OrderProcessor 构件还有一些请求端口,它指定了其他参与者提供的需要:结账、日程安排及传递。
每一个服务和请求交易点都可以涉及到一个协议,该协议指定了怎样使用提供的和需要的界面操作。例如,结账的请求端口需要
Invoicing 界面进行价格计算并发送传递的价格。但是,计算传递的价格可能还需要一段时间,于是 OrderProcessor
通过它所请求的端口提供 InvoiceProcessing 界面,这样结账服务提供商就可以在就绪的时候发送结好的账目了。
Order Processor 执行设计模型
现在我们已经完成了服务模型的架构化结构,并在服务提供商的外部视图中得到它。接下来要做的事情是为 OrderProcessor
构件提供的 processPurchaseOrder 服务操作设计一种方法。该方法必须遵循任意实现的服务契约或者实现的服务规格,以及定义操作的服务规格。
内部的结构
OrderProcessor 服务提供商通过它的购买服务端口提供了一种单个的服务规格,Purchasing。该服务指定了一种单个的操作,processPurchaseOrder。服务提供商必须为所有提供的服务操作提供一些方法。该例使用
Activity 作为 processPurchaseOrder 服务操作的方法。具体这是怎样实现的显示在提供服务的
OrderProcessor 构件的内部结构中。OrderProcessor 内部结构是通过图表、界面、类及活动获取的,如图
7 中的 Project Explorer 视图和 图 8 中的组合结构图所示。
图 7 中的 Project Explorer 视图显示了 OrderProcessor 提供商部分的列表以及每一个提供的操作的方法(行为)。该例中采用的习惯是使用一个与其参与者同名的类图,以显示
图 6 中显示的外部视图。
图 7. OrderProcessor 的结构
Project Explorer 视图显示了
OrderProcessor
与构件相同名字的构件结构图提供了服务提供商结构的内部视图。该图直接位于图 8 中 OrderProcessor
服务提供商下面。这些习惯使得协调服务参与者的内部视图及外部视图,以及处理与构件相同的图表变得更加容易。
图 8 中所示的 OrderProcessor 构件结构提供了服务提供商的内部结构的一个概述。这再次显示了组成参与者静态结构的部件(端口与属性)。
图 8. OrderProcessor 服务提供商的内部结构
OrderProcessor 内部结构图
OrderProcessor 构件的内部结构是简单的。它由所提供的和所需要的界面的服务与请求端口,加上维持服务提供商状态的一些其他属性组成。ID
属性用于识别服务提供商的实例。该属性将用于在运行时联系消费者与提供商。schedule 与 shippingInfo
是 processPurchaseOrder 服务执行的实现中会使用到的信息。
注意:
在本例中,所有的服务都是非论述的,但是提供和使用服务的参与者通常不是这样的。
提供服务操作的方法
服务提供商提供的每一个服务操作必须通过一种行为或者操作来实现:
一个是操作的方法的行为(Activity、Interaction、StateMachine 或者 OpaqueBehavior)
Activity 中属于构件的 AcceptEventAction (对于异步访问)或者 AcceptCallAction
(对于同步的请求或者回应访问)
这就使得单个的 Activity 能够拥有不止一个当前的进入点,而且它能响应 Business Process
Execution Language(BPEL)中多个接受活动。这些 AcceptEventActions
通常用于处理访问以从其他的异步 CallOperationActions 中返回信息。
OrderProcessor 构件有服务实现两种形式的范例。processPurchaseOrder 操作拥有与
Activity 方法相同的名字。如图 9 所示,该活动是提供服务操作的服务提供商所拥有的行为。
图 9. processPurchaseOrder Service Operation 的实现
processPurchseOrder Activity
图
该图十分紧密地相应于 IBM? Rational? Requirements Composer Business
Process Modeling Notation (BPMN)业务进程。InvoiceProcessing
和 ScheduleProcessing 服务操作通过 processInvoice 与 processSchedule
来实现并接受进程中的变更。注意界面中相应的操作会标记成接受,以指示响应由其他参与者发送的访问事件的能力。
注意:
这些操作将不会得到接受,除非 processPurchaseOrder 活动正在运行而且控制的流程达到了两个
Accept Call 操作。这意味着操作的执行可以决定什么时候其他的操作将会得到回应。
组合参与者
OrderProcessor 构件现在已经是完整的了。但是让其能够在任意的环境下,手动或者自动执行(实现),OrderProcessor
参与者必须联系能够满足请求的参与者。否则,请求端口上激发的操作将得不到执行,因为没有参与者去执行它们。剩下来还有两件事要做:
首先,我们需要创建一个参与者,它组合了其他能够向合适服务提供 OrderProcessor 请求的参与者。
然后我们需要将 OrderProcessor 服务提供商与为需求建模的服务结构联系起来。
这就产生了一个潜在活动参与者的完整组合体,可以在一些执行环境下运行(包括手动的过程)。
这个部分处理了新的 Manufacturer 参与者中组合的参与者。接下来的部分讨论了尝试让方案回到它所遵循的服务架构部分。
图 10 中显示的 Manufacturer 参与者代表了一个完整的参与者部分,该参与者将 OrderProcessor
服务提供者与提供受请求服务的其他服务提供者联系起来。这个参与者是其他参与者的一个组合体,它提供了所需要的所有信息,以完成订单处理和购买服务。
图 10. 组合 Manufacturer 部件
Manufacturer 的内部结构图
Manufacturer 参与者是引用 OrderProcessor、Invoicer、Productions
及 Shipper 参与者实例的组合体。销售参与者的结账服务与 Invoicer 参与者的结账服务是相互联系的。这是一种有效的联系,因为
OrderProcessor 参与者的结账服务的服务界面与 Invoicer 参与者的结账服务相同。
联系的服务与请求意味着参与者同意根据服务界面通过一种服务渠道来进行交互。这就是说,它们同意遵循需要的协议。服务界面定义了联系协议中参与者的角色。orderProcessor
消费者的结账请求端口与 Invoicer 提供商的结账服务端口之间的服务渠道连接器创建了参与者之间的协议。这个过程需要通过服务渠道的任意交互形式,以遵循服务界面的协议。
其他的消费者和提供商按照相似的方法进行联系。联系的服务可以提供不同的绑定形式。服务交互点之间的服务渠道可以指定实际的绑定形式以使用。
服务价值链
将 orderProcessor 请求与 Invoicer 服务联系起来的服务渠道,建立了价值链中的联系。orderProcessor
参与者的请求代表了通过结账请求端口所要达到的目标,以及服务期望的质量。所有这些信息在服务界面中获取,以定义请求。与之相反
Invoicer 的服务通过它的结账服务端口及它提供的功能来代表它的价值,以支持该价值的成就,参与者愿意并且能够实施的服务的质量。
关键点
SOA 的关键在于以一种能够满足业务目标的方式建立这些服务的价值链,同时降低参与者之间的耦合度。降低开发好的服务结构所造成的参与者之间的耦合度,可以增加业务的敏捷性。
Manufacturing 参与者现在就是完整的,并且已经可以在一些执行环境中执行和部署了。它引用了所需要的全部服务参与者以充分地执行
processPurchaseOrder 服务操作。在它部署之后,其他的服务消费者可以绑定至 Manufacturer
参与者的购买服务并激发服务操作。
遵循服务架构
本例中所要做的最后一件事就是将我们的方案与在第一篇文章中,第 1 部分:服务实现所设计的服务架构联系起来。我们的方案已经与业务动机和策略联系起来,因为在第
1 部分中识别的服务界面揭示了实现业务战略和目标的业务功能。在一个更广泛的例子中,我们可以使用 OMG
Business Motivation Model (BMM)来获取业务动机和战略的一个更加复杂的图。这样一个模型不仅仅包括业务目标,还包括了促进业务变更的影响,变更包括识别那些模板、支持那些目标成就的战略和战术、评价业务在降低风险与增加回报方面的潜在效果等等。这可以用于将方案中的服务直接与业务上的处理联系起来,因此识别了校正构造的价值。
本文中并没有变更 Manufacturer 参与者转化为特定平台实现的方式。将参与者与服务架构联系起来,只描述了参与者实现了架构指定的需求的方式。这并不会影响服务提供商的执行,或者它转化为平台方案的方式。
但是,联系要比一个简单的附件更加复杂。特别需要指出的是,它显示了服务提供商在服务架构中发挥的作用,以及在参与者方面的限制因素是如何对结构和业务施加影响的。它为变更提供了更高的追踪性和支持,以及使用模型确认的能力以确保方案能够满足它们的需要。
图 11,摘自“第 1 部分:服务实现”,显示了处理购买订单的服务架构。协作使用添加至 Manufacturer
参与者以指示它所满足的服务架构。
图 11. 处理购买订单的服务架构
制作者的服务结构图
协作使用,也就是图 12 中所谓的结构,是来自第 1 部分制造者架构服务架构的一个实例。它指定了 OrderProcessor
服务提供商遵循服务架构。绑定的角色指定了服务结构中所扮演的角色。例如,结账的参与者扮演了 Invoicer
的角色,而 orderProcessor 参与者扮演了 orderHandler 的角色。
图 12. 遵循服务结构
Manufacturer 结构图
这些绑定的角色与前面部分中描述的服务渠道连接器没有关系。服务渠道连接器用于将参与者组合中的消费者请求与提供商服务联系起来。角色绑定指定了各个部件在服务结构中扮演了什么角色。角色绑定的理解可以严格,也可以宽松一点。
严格 意味着部件必须与它们绑定的角色的类型是协调的。
宽松 意味着部件需要根据结构来发挥其作用,但是模型认证并不需要可能也不能确认角色和部件的协调性。
这可能是因为,服务结构是不完整的,或者只是以一种不规范草图的形式存在。
显示 SOA 方案怎样执行业务结构需要做一些其他的工作,以制定服务结构与角色绑定。但是它为管理变更提供了很大的便利之处。模型查询可以用于决定哪些参与者实现了业务需求。需求上的任何变更,都可能导致服务结构上某个角色的变更。建模者可以直接切换到扮演某种角色的部件那里,以决定对部件指定类型的服务界面需要做什么变更以应对需求上的变更。
模型确认还可以用于决定是否有一些角色发生了变更,以及 SOA 方案中部件所发挥的作用是否不再能够执行这个角色所赋予的责任。这要比构型一致的附件功能更加强大,该附件没有支持的语义意义或者用例实现的宽松语义。SOA
方案与业务需求之间规范可确认的联系,可以确保方案是业务相关的,满足需求,并使得敏捷方案能够快速适应变更。
本文的总结及接下来的内容
现在我们已经完成了服务的识别、指定和实现,并指明了提供和使用服务以满足业务目标的参与者。结果是一个以平台为中心、以技术为中心但是却相当完整的服务方案结构。
为了能够真实运行方案,我们需要创建一个平台执行,它与服务模型中获取的结构化设计决策相一致。我们可以将模型作为指南使用以手动创建该方案。但是这种方法是比较繁琐、容易出错、费时,可能还需要一个有着高度技巧的开发员以确保结构化的决策得到合适的执行。
手动创建方案显然是可能的,使用模型作为指南可以帮很大的忙。但是拥有一个完整、规范且确认的模型给我们了一个机会,去利用模型驱动开发(MDD),以从模型中创建一个方案草图,然后在特定平台的编程环境中完成具体的编码活动。而这正是本系列文章的下一篇也就是最后一篇文章的主题,这篇文章就是“使用
soaML,面向服务架构建模语言来建模:第 5 部分:服务的执行”(参见“本系列文章更多内容”)。在那篇文章中,我们使用
Rational Software Architect 的 UML-to-SOA 转换特性,来创建一个可以直接在
IBM WebSphere Integration Developer 中使用的 Web 服务方案,以执行、测试和部署所完成的解决方案。
第 5 部分: 服务实施
本文的创作背景
前面文章中的步骤创建了一个满足业务需求的完整 SOA 方案模型。因此,我们知道了该方案架构满足的需求,以及当需求变更时需要改变什么。
为了部署和运行这个方案,我们需要创建一个实际的执行,它与模型中获取的结构性和设计决定相协调。我们可以使用模型作为一个向导来手工创建该方案。但是可能这很容易出错,繁琐且费时,并且需要一个有高度业务能力的开发员以确保实际的决定作出了正确的实现。很有可能手动创建方案,使用模型作为指南是非常有用的。但是拥有一个完整规范确实的模型,能够给我们一个机会去利用模型驱动开发(MOD),来从模型中创建一个或者多个方案草图,然后在特定平台的编程环境中完成具体的编码工作。这就是本文的主题。我们将会使用才
Rational Software Architect UML 到 SOA 的转变特性,来创建一个可以在
WebSphere Integration Developer 中直接使用的 Web 服务,以执行、测试和部署完成的方案。
有了本系列的各篇文章,我们会使用已存在的 IBM Rational 工具来构建方案工件,并将它们联系在一起,这样我们就可以根据需求来确认方案,并且更加有效地管理变更。另外,通过向
IBM Rational Software Architect 中的 UML 模型来添加 OMG SoaML
Profile,我们扩展了统一建模语言(UML)。表 1 提供了开发该范例将会使用全部过程的总结,以及用于构建工件的工具。
表 1. 开发进程角色,任务和工具
开始时让我们评审在前面文章中创建的服务以及服务参与者,使用 SoaML,面向服务架构建模语言建模:第
1 部分:服务的实现(见于“本系列文章的更多内容”)。
服务规范以及实现评审
图 1 提供了完整范例的概述。顺序管理包包含了关键的模型元素:Purchasing ServiceInterface
与 OrderProcessor 以及 Manufacturer 参与者。Ordermanagement
包会从其他的包中导入模型元素。客户关系管理(CRM)包包含了定义用于实现服务的持续性实体的域数据模型,以及用于在服务参与者之间交换信息的服务数据
MessageTypes。服务数据是满足特定服务需求域数据上的视图(一个选择和项目)。
信用、产品和传递包分别定义了 Invoicer、Productions 以及 Shipper 参与者,以及他们相应提供的服务界面。OrderProcessor
是提供购买服务,并为结账、日程安排和传递使用服务。
Manufacturer 参与者是联系在服务价值链中其他参与者的引用。这就是说,orderProcessor
拥有结账者、产品和传递者部件提供满足的需求。Manufacture 参与者还提供了一个购买服务,但是它是通过将其委托给它的
orderProcessor 内部构件而实现的。所有的服务操作都有一种方法,去指示服务实际上是如何执行的,以及被消费的服务实际上是如果被使用的。
Manufacturer 参与者还会坚持在第一篇文章“使用 SoaML,面向服务架构建模语言建模:第 1
部分:服务的识别”中定义的 Process Purchase Order 服务架构。Manufacture
参与者的部件会限制于参与者的角色,以显示服务模式是如何遵循和实现的。这就可以确保方案遵循企业结构指导原则,而且它提供了结构部件与方案部件之间的追踪性。
图 1. 处理购买订单概述
处理模型的购买订单图
服务建模最佳实践
UML 2 建模通过使我们从具体的细节过程中抽离出来,来提高对系统的理解能力。尽管如此,建模并不是一副万灵药,而有意义的模型图仍然可以请求企业去创建和理解。支持计算的通用模型,是需要的自然结果,可以用于广泛的程序域以及各种层次的抽象级别,而且它代表了特定平台执行模型的语义。另外,活动模型样式或者操作的类型需要得到限制,以支持那些模型向目标执行平台的有效转换。
在这种情况下,目标平台是 WebSphere Integration Developer Web 支持的服务以及
用于实现 Web 服务的 SOA 编程模型,第 1 部分: IBM SOA 编程模型简介。包含的业务目标(XSD)、界面(WSDL)、模块集合(SCDL,Open
SCA 的 IBM 处理器,有时也叫做“经典 SCA”),处理(BPEL4WS:Web 服务的业务进程处理语言)以及
Java?构件。为了在这个特定的 Web 服务平台上支持 UML 模型的转变,我们需要遵循服务建模最佳操作。我们先将对象管理组(OMG)SoaML
标准概述转换为 SOA 方案架构,然后使用一个特定的建模样式,以产生可以转换为 Web 服务的模型。
UML 一般使用概述来定制。所谓的 概述定义了一系列的构造型类,可以使用附加的属性以及关系来扩展一个或者多个
UML 元类。概述应用于 UML 模型以使用这些扩展。这些应用的概述通常支持模型驱动架构中两个目的:
首先,对概述最常用的就是定制想要支持的抽象程度。在这种情况下,我们对我们的 Purchase Order
Process 模型应用 OMG SoaML 概述,以扩展 UML 好支持服务建模。该概述中的许多构造型都会简单地澄清怎样使用
UML 元类来为 SOA 方案建模,并限制在 UML 中完成的任务,以确保 SOA 模型反映了 SOA
原则。例如,<<Participant>>构造型用于指示一个对服务消费者或者提供商建模的
UML 构件。举一个限制的例子,SoaML 需要 <<Participant>>
构件实现或者使用的所有界面,以通过服务和请求端口(UML 端口)进行处理。这就是降低联系的消费者与提供商之间的耦合度,而不是整体的构件。然后,有一些界面更改,只有那些更改过的端口才会得到检查,以响应更改,而不是与构件联系的所有端口。
模型驱动架构(MDA)的第二个目的,是支持特定平台的标记。这些标记由其他的构造型以及属性组成,这些构造型和属性用需要的信息来“标记”一个模型以将其转换为特定的平台。例如,在转换为一个
Web 服务容器时,一个特定的 UML 包可能会需要有特定的统一资源标记(URI)。
有时,概述的这两个目的会合并在一起。例如,对 UML 的扩展以支持关系数据建模,,它由单个概述组成,概述为实体-关系-属性(ERA)数据建模扩展
UML,并提供了需要的标记以将 UML 域模型转换为 IBM?Info Sphere?Data Architect
逻辑性数据模型(Lames)。
在其他的情况下,当其他的概述用于驱动转换时,还有一个概述可以用于支持建模。例如,考虑一下在 Java?Platform,Enterprise
Edition(JEE)上执行的 SOA 设计建模。对同一模型同时应用 SoaML 概述与 Enterprise
JavaBeans?(EJB)转变概述,可以帮助使用程序。SoaML 概述构造型将会应用于模型元素,以支持服务建模;尽管如此,EJB
转变概述构造型将会应用于模型元素,以指导 Rational Software Architect UML
到 EJB 转变的执行,同时生成执行代码。当然,相同的 SOA 模型还可以使用 SoaML 概述标记,来生成
Web 服务。它将会忽略掉 EJB 转换的标记。
接下来的部分描述了对 SOA 模型的最佳建模操作方式,这些 SOA 模型会转换为 Web 服务,特别是
IBM?SOA 编程模型中执行的特定 Web 服务并为 WebSphere Integration Developer
所支持。
数据建模
服务操作参数的类型会是 UML Primitive Type、DataType 或者 SoaML<<MessageType>>DataType
中的一种。建模员不应该假设数据的位置,值访问或者引用语义访问,也不应该假设任何清晰的并发管理设备。假设服务执行会在数据的临时拷贝上进行,数据应该从它的原始源来转移、转换或者即转移又转换。这就确保在服务消费者与服务提供商之间的数据的耦合度降到最低。
SoaML 支持服务操作的远程程序访问(RPC)或者文件中心样式参数。RPC 样式支持多种输入和输出参数。文件中心样式最多允许一个输入和一个输出。使用
SoaML MessageType 参数来指示文件中心的样式。
服务建模
正如在 SoaML 概述中指定的那样,一个服务参与者必须通过服务端口实现或者使用所有的界面。这就确保与构件相联系的服务参与者之间不会发生耦合。
活动建模
一个联合的服务提供商会为每一次操作提供一种行为,以为服务操作的方法建模。
注意:
所谓联合的服务提供商就是一个既不抽象又不是<<specification>>构件的构件。
可以使用任意的行为,但是如果模型目标平台是 Web 服务,那么就很方便使用可以轻松转换为 BPEL4WS
的活动。例如,Order Processor 服务提供商构件的活动模型,就是 processPurchaseOrder
操作的方法。关于活动还有一些事情需要解释:
方法行为的签名必须匹配其规格操作。
操作的输入与输出部分会在包含操作的右下角找到,而且它们会顺时针排列到右下角。该帧排序响应于访问操作参数的顺序,而目标输入帧会成为第一个帧,而操作的类型会成为最后的输出帧。目标输入帧代表了操作请求发送至的目标对象(例如,拥有操作的标识符)。
输入与输出帧类型通常不会得到设置,因为可以从相应的参数中得到它们。
该活动并不使用对象流来简化图表的创建过程。相反,操作上输入与输出的名字,会标上范围内背景标识符(拥有活动的类)中的参数、变量或者结构性特性。UML
2 都支持它们,但是使用它们中的哪一个取决于您个人的偏好。
活动参数节点(在活动的左边和右边)并没有得到使用。相反,活动的参数(它必须响应于规格操作的参数)会在输入与输出帧上得到直接的引用。
活动分区被设置为代表包含活动的端口或者服务端口。所有的调用和所有的事件都会通过端口来接受。在这种情况下分区并没有得到命名,因为代表的属性提供了足够的信息以识别分区。
访问操作的目标输入帧并没有得到设置。作为一个选择,活动分区代表了该分区中访问调用的服务端口。它们叫做 UML
2 中的 <<instance>> 分区,并拥有定义完善的语义。目标输入帧也可以得到设置,但是这可能会是多余的。
Accept Call 操作的 returnInformation 帧与访问操作的目标输入帧得到相同的处理。它还是活动分区代表的端口,而且它通过接受的访问来代表交易点。
任务表达与模糊操作一起显示,而操作的名字包含了引用变量、参数和结构化特性的任务表达。任务声明中的 lvalue
与 rvalue 由一个冒号加等号隔离开来( := )。
对象上的 Guard 表达式与控制流是引用变量、参数和结构化特性的 Java 或者 XPath Boolean
表达式。
对象流上的数据由流程的名字引用。
对象流上数据的类型由它的来源决定。
这些规则用于简化活动建模过程,简化活动图,并更好地响应从 BPEL 中生成的项目。
转换为 Web 服务
转换需要使用转换配置。
配置转换
您可以选择 File > New > Other > Transform Configuration,来创建一个转换(见于图
2)。
图 2. 创建一个新的转换配置
'选择一个向导 ' 屏幕视图
对于本例我们将会使用从 UML 到 SOA 的转变,如图 3 所示。
图 3. 选择从 UML 到 SOA 的转变
'新的转变配置 ' 窗口
大多数的转变的配置由三个基本的部件组成:
选择转换源元素
选择(或者创建然后选择)目标元素
配置转变属性
可允许的源元素是由选择的特定转变定义的。通常来说,最好只转换整个的模型,而不是模型的私人部分。这就可以确保模型,它代表了私人版本的资源,被当作模型转变方面的
汇编单元。通过确保工作区内资源的更改,响应于应该处理的转变,来简化模型管理以及转变依赖性处理过程,以确保得到的工件与它们的源元素保持同步化。例如,您不会想到
Java 类中的私人方法,并且只汇编这种方法,然后为剩余的类将其插入到比特代码中。在一个快速变更的环境中进行管理可能不太现实,它可能需要您本人,而不是构建器和汇编器去知道由于更改发生而可能要求汇编的所有附件。
在本例中,PurchaseOrderProcess 模型是源,而工作区作为目标被关闭。所有转换的模型都被置于新的
WebSphere Integration Developer 项目(见于图 4)中。
图 4. 配置转变源与目标
屏幕上所选择的转变源
转换配置参数代表了没有包含在模型中的转变选项。一般来说,控制针对总体选项,而不是对应用到一个特定模型元素上的选项。UML
到 SOA 的转变只有很少几个转变选项,如图 5 所示。
图 5. 配置转换特性
两列:属性与值
处理 UML 元素而不将构造型设置为 True,意味着 SoaML 概述实际上是可选的。数据类型,构件和活动会转换为
Web 服务方案而不需要任意的构造型,或者构造型会离开特定的模型元素。但是,应用 SoaML 构造型以简化服务模型,是一个比较好的建模操作。
这就会完成配置将 PurchaseOrderProcess 模型转换为一个 Web 服务方案。项目会位于工作区中。
运行转换
执行 PurchaseOrderProcess2WebServices 转换是十分简单的:
选择在前面部分中创建的 PurchaseOrderProcess2WebServices.tc 转换配置文件。
从弹出菜单中,选择 Transform > UML to SOA。
转变配置中选择的转变得到了执行,因此将源模型转换为 Web 服务工件,并将结果得到的 WebSphere
Integration Developer 项目置于工作区内。然后您可以启动 WebSphere Integration
Developer,并将已经存在的项目导入到 WebSphere Integration Developer
工作区内,以完成、部署和测试结果。
技巧:
如果模型发生了变更,那么您需要返回这种转变。
转变的结构如图 6 所示,使用 Project Explorer 中的 Modeling 视图。
图 6. 转变结果
结果的 Project Explorer
视图
检查结果
UML 到 SOA 的转变配置会在一系列的 Eclipse 项目中置放结果的元素。这些项目要么是 WebSphere
Integration Developer 库要么是模块项目,如下面的子章节中所述。
库项目包含了由其他项目所共享的业务目标、界面和模块导出。
模块项目为 UML 服务模型中的每一位参与者都包含了一个模块执行。
您可以将这些项目导入到 WebSphere Integration Developer 工作区内。
技巧:
您可能会发现关掉 Automatic Build 会非常的有用,否则直到所有的项目都被导入之后,导入才会加速。
模型与库
转变配置中每一个模型的源,是用与模型相同的名字转换为一个 WebSphere Integration Developer
库。该库为源模型中的每一个类和数据类都包含了一个 XSD 元素,为每一个 UML 界面都包含了一个 WSDL
定义。这些库定义了所有 WebSphere 模块使用的业务目标与界面,其中的模块是从转变配置的选择源中的构件所生成的。
图 7 显示了 WebSphere Integration Developer 中导入生成的库以及模块项目,同时
PurchaseOrderProcess 被展开了以显示生成的业务目标与界面。注意 WebSphere
中的文件夹与名字域,直接响应于 UML 服务模型中的包结构。这就可以确保不同的资源与工具之间稳定的名字域管理与再使用。
图 7. ProcessPurchaseOrder 库及其业务目标和界面
网络域中的 PurchaseOrderProcess
XSD 与 WSDL
让我们细看一下业务目标与界面,并将它们与它们的 UML 源代码相比较。图 8 使用 WebSphere
Integration Developer Business Object 编辑器,该编辑器在 PurchaseOrder
业务对象上打开,以显示从服务数据模型中生成的 XSDs,在“使用 SoaML,面向服务架构建模语言来进行建模:第
3 部分. 服务的实现”中有所论述。正如您可以看到的那样,XSDs 可以精密地响应于它们的源数据类型。点击图片以查看生成的源。
图 8. 从服务数据模型中生成的 XSDs
PurchaseOrder 项视图
每一项 UML 界面都会转换为一个 WSDL portType。图 8 中为 Invoicing 界面生成的
WSDL 显示在图 9 中。点击图片以查看生成的 WSDL 源。WSDL 同样类似于 UML 界面。
图 9. 为 Invoicing 界面生成的 WSDL
Invoicing 项视图
构件以及模块集合
UML 服务模型中的每一项服务提供商构件,都会转换为一个 WebSphere Integration Developer
模块。集合服务消费者(有时也叫做 用户)和提供商并没有什么 Web 服务。因此,WebSphere Integration
Developer 会使用一个属性,也就是 服务组件体系结构(Service Component Architecture)(SCA)的早期版本。可以在使用服务构件描述语言(SCDL)的
.component 文件中找到模块集合,它是服务构件集合的 XML 文件语言。一些公司会协作以为 SCA
开发一种标准。见于 Open SOA 网站以得到进一步的信息。
UML 到 SOA 的转变会为每一个参与者都创建 WebSphere Integration Developer
模块,以最大化再使用的程度。SCA 模块不能从其他的模块中收集到。但是,它们可以从其他的模块中导入服务,然后间接地使用它们。因此,UML
中参与者之间的联系作为 WebSphere Integration Developer 中导入与导出之间的联系而执行。例如,您可以考虑一下
图 1 中所示的 Invoicer 服务提供商。
图 10 显示了相应的 WebSphere Integration Developer 模块集合。每一个服务和请求端口都会创建模块导入和导出。SCA
不能为相同的交易点支持提供的和需要的界面,因此提供和需要界面的服务和请求端口都会创建隔离的导入与导出元素。invoicingExport
服务导出了提供的结账界面;尽管如此,invoicingImport 导入了 Invoicer 服务提供商的结账服务端口所需的
InvoiceProcessing 界面。
图 10. Invoicer 模块集合
为 Invoicer 所收集的 WID SCA
注意模块的名字。一个模块就是一个 eclipse 项目,但是因为模块是可再用的元素,所以它必须管理像其他可再用元素之类的名字冲突。UML
到 SOA 转变使用规则,基于服务提供商构件完全有效的名字用于创建模块项目名,由它包含的包决定。这就产生了很长的模块名,由于
URLs 长度的限制,名字过长可能会在 Windows 平台上产生一些运行上的问题。只要名字冲突在一定的背景下解决了,那么这些模块名可以轻松地重构成更短的名字。
Productions 构件会产生另一个模块集合,如图 11 所示。该模块没有含有导入,因为服务端口并不需要什么界面。
图 11. 产品模块集合
为 Productions 收集的 WID
SCA
这些模块都使用一个 BPEL 过程来实际执行相应服务提供商构件提供的服务。在接下来的部分中会显示这种方法的具体内容。
查看一下图 12 以查看为 OrderProcessor 构件创建的模块集合。
图 12. OrderProcessor 模块集合
为 OrderProcessor 收集的
WID SCA
OrderProcessor 服务提供商为结账、日程安排以及传递服务提供了购买服务以及请求。将图 1 中的消费者与提供商构件联系的服务渠道,会作为
OrderProcessor 模块中的导入执行,以导出相应服务提供商的导出。这就允许 WebSphere
Integration Developer 中模块得到有效的重复使用,并将 UML 服务模块独立于 SCA
的发展过程之外。当 SCA 得到标准化之后,UML 服务模型就不再需要变化了;只有转换才有必须要得到更新。
活动与 BPEL 过程
服务提供商提供的每一项功能性性能(操作)必须得到一定程度的执行。执行要么使用每一项操作的方法,要么使用一些其他行为中的方法或者
Accept Call 操作来在 UML 中设计执行。通过让操作者去决定什么时候愿意且有能力响应一条请求时,,而不是在服务消费者调用操作时立马就需要响应请求,后一种方法使消费者与提供商之间的耦合度得到了有效的降低。
WebSphere Integration Developer SCA 采取不同的方法。每一个导出都必须限制于集合中的某个构件,该构件为界面中的操作提供了一种执行方法。SCA
中的构件拥有以下的执行类型:
人们的任务
Java
进程
角色组
状态机
图 12 中的 OrderProcessor 服务提供商通过它的购买服务提供了一个单一的功能性性能以处理购买订单。这个操作的实现就是
UML 服务模型中的操作。UML 到 SOA 的转换从该进程中创建了一个 BPEL 进程,并将其作为导出操作的执行方案来使用。
图 13 中的 BPEL 进程非常相似于 OrderProcessor 参与者中的 processPurchaseOrder
活动。UML 活动是怎样转换为一个 BPEL 进程的具体细节信息,可以在 Rational Software
Architect 的 Help 部分中找到。
图 13. OrderProcessor 进程构件与执行
为 OrderProcessor 生成的
BPEL
解除耦合界面以及执行方案
正如前面所述的那样,WebSphere Integration Developer SCA 执行方案通过书写一个导出来提供功能,它向实现所提供服务的构件提供了一个界面。因为一个构件可以有一个执行类型,所以该导出所有界面提供的所有操作,都必须按照相同的方式执行。这就将执行类型与一个导出的所有界面联系了起来(所有导出可以由一个构件执行)。如果开发员想要更改一个特定操作的执行类型(例如,从一个任务更改为以
Java 实现的自动化服务),那么界面必须得到重组,以让不同的构件能够使用不同的构件执行类型。反过来,这又需要对那些界面的所有消费者都作出更改。这种界面设计耦合起来以执行的方法,阻止了
SOA 方案本来能够支持的商业目标的实现。
UML 并没有该规格以及执行耦合。提供的每一项操作可以拥有一个方法行为,方法行为是一个活动、交流、状态机或者模糊行为(代码)。建模员会独立地设计每一项操作的执行方案。这就可以产生一种情况,那就是相同的服务提供商构件对通过相同的界面中提供的不同操作,使用不同的行为类型。我们需要有一些方法,将这些服务提供商转换为
Web 服务。
还有另外一个因素需要考虑一下。构件是通过 UML 来得到实例化的,而不是它们拥有的行为。因此,实例化特征与生命周期与相同构件中的所有行为相同。另外,构件为所有它拥有的行为都建立了一个背景或者范围,因此允许这些行为能够共享对构件状态(属性和端口)的访问。因此,在转换为
Web 服务时,我们必须要有一些东西去管理这些特征、声明周期,并共享能够实现 UML 语义的状态。这就是引入业务进程执行语言(BPEL)的原因(见于参考资料
以得到更多关于 BPEL 的信息)。
我们不是创建一个单独的 SCA 构件,以执行模块集合中参与者的每一项操作,而是创建一个单独的 BPEL
进程以响应构件自身。您将会注意到图 13 中 BPEL 的名字是 OrderProcessor,,与 OrderProcessor
服务提供商相同,而不是 processPurchaseOrder,也就是提供的操作的名字。
让我们细看一下图 14 以查看 Productions 构件是怎样转换为 WebSphere Integration
Developer Web 服务的。
图 14. Productions 参与者
Productions 参与者的类图
注意为 requestProductionScheduling 设计的执行方法使用一项 Activity(具体内容不知道),但是
sendShippingSchedule 使用 OpaqueBehavior 以及 Java 代码中提供的执行方法。该服务提供商集合的模块如图
15 所示。
图 15. Productions 服务提供商执行方法
为 Productions 生成的 BPEL
的图
BPEL 进程为 Productions 服务提供商构件而创建。服务提供商的独特属性用于定义活动中所有
Invoke、Receive 与 Reply 活动的相关性。构件提供的每一项操作都由该进程的一个片段执行。以一个
pick 元素开始的进程用于处理每一项操作请求。然后每一项操作会创建一个范围,以为 UML 行为中定义的变量提供一个位置。然后范围包含了转换行为的结果。如果行为是一个
UML 活动,那么范围就会包含从活动中生成的 BPEL,如果行为是一个用 Java 语言写成的 OpaqueBehavior,那么行为的实体会复制到范围中的
Java 活动。如果行为是由 HTML 或者 JavaServer?Pages(JSP)语言写成的 OpaqueBehavior,那么会向范围中添加一个
Human Task 活动中。
这就提供了界面及其执行的完整解除耦合的操作。例如,如果建模员或者开发员决定将一项服务操作从任务中更改到自动化的
Java 代码中,那么只有该操作范围内的任务元素才会需要更改。客户不会意识到执行发生了更改,直到他们注意到服务运行的更快了,所以他们不需要再去做大量繁琐的工作为止。
完成方案
UML 到 SOA 的转变并没有生成完成的方案。这就是因为将执行内容集成到模型中的努力,要比使用编辑器将其集成到特定平台的工件中要困难的多。UML
2 Activities 还有一些特性没有转变成 BPEL。在未来的版本中会加入这些内容。在 Rational
Software Architect 中的 Help 中可得到特定版本可得到的具体内容。
一般来说,WebSphere Integration Developer 需要做一些或者全部的以下开发活动。
如果模型中没有提供它的话,为模糊的行为添加 Java 代码。就算模糊行为的实体中提供了 Java 代码,也很容易产生错误,因为
Content Assist feature 和 Java(或者一个操作语言)汇编尚未与 Rational
Software Architect 中的建模功能相集成。
为业务进程添加相关性。需要相关特定信息以识别构件的实例,UML 到 SOA 的转变尚不支持这种实例。而未来的版本会支持。
为任务创建一个用户界面(UI)。UML 模型可能含有模糊行为中的 JSP 或者 HTML。但是,就像 Java
源代码一样,这可能是不完整或者不合适的。集成开发员可能想要使用 Human Task 编辑器,Page
Designer,或者其他的工具来创建完整的任务,它有合适的外观并完成程序 UI。
配置监视器模型。目前,UML 到 SOA 的转变并不会创建监视器信息,以评价关键的性能指示器(KPIs),该指示器可能被建模成服务和服务提供商的限制性因素。集成开发员可以使用
WebSphere Integration Developer 中的Monitor Model Editor
工具,以配置哪些数据应该收集起来以模拟更新和业务评价。
系列文章的总结
使用 IBM Software Services 概述来导出 Rational Software Architect
中的建模服务(见于“本系列文章更多内容”以得到最近的四篇文章)。第一篇文章,使用 SoaML,面向服务架构建模语言:第
1 部分:服务的识别,涉及到怎样使用业务过程和服务架构,来指定一系列的服务应该怎样联系起来,以及组合起来以完成一些目标。这些需求通常用于指定完成了什么目的。然后服务架构可以是十分有用的,以识别提供实际业务价值的服务。
使用 SoaML,面向服务架构建模语言建模:第 2 部分:服务的规定展示了怎样为服务界面的具体内容建模。如果一项服务可以解决问题的话,那么一个服务界面定义了潜在消费者需要了解的事情。如果是这样的话,以及实际上它是如何使用的。服务界面还决定了潜在消费者所需要的信息,以决定服务是否能够解决问题,如果能解决的话,怎样使用它。服务界面还定义了需要什么服务的提供商以完成服务。
接下来的文章,第 3 部分. 服务的实现和第 4 部分. 服务的组合,展示了怎样设计和建模参与者,这些参与者要么提供服务,要么消费服务,以及这些服务操作是如何被执行的。文中还描述了服务提供商是如果指示结构与将他们联系在一起的服务契约,服务提供商会参与到业务目标、目的、进程、需求以及结构指导原则。
这篇最后的文章描述了怎样使用 IBM UML 到 SOA 的转变,来在
IBM WebSphere Integration Developer 所支持的 Web 服务平台上实现服务。WebSphere
Integration Developer 支持一种 SOA 编程模型,该模型与在 Rational Software
Architect 中获取的识别、规定和实现设计相协调。通过使用 WebSphere Integration
Developer,您可以完成服务编程,然后为任务生成一个 UI,部署并测试您的程序。
上篇:使用面向服务体系架构建模语言建模(上)
|