现在我们已经浏览了在 IBM WebSphere Application Server V6 中支持的消息传递资源的基础(在第 1 部分中),描述了我们将在本系列文章中使用的业务场景(Posts-R-Us 公司),并看到了如何创建消息传递总线的实例(在第 2 部分中),现在到了该做些实际工作的时候了!
在第 3 部分中,我们将向您展示如何创建一个简单的点对点的基于 JMS 的消息传递的应用程序。这个应用程序由一个发送部分(在 J2EE™ 客户端应用程序内运行),和一个接收部分(以消息驱动 bean 为代表)组成。在创建此应用程序的过程中,我们将看到在应用程序服务器中通过消息总线发送 JMS 消息所必需的设置。
在接下来的业务场景中,我们将假定无论包何时被传递给消费者,消息都必须发送给 Posts-R-Us 的主系统以便确认此传递。该确认消息异步传送,也就是,没有需要的响应,此消息简单地排列到主系统中用于处理。
可能您现在认为,在 MDB 中发送消息给 JMS 队列,并从那儿进行接收是非常令人兴奋或新鲜的。您是对的。然而,它之所以有趣是基于以下事实:消息通过消息传递总线正确发送到目的地。它可以使我们使用中介来应用可选的消息传递的处理,比如过滤消息内容或者路由到其它不同的目的地,仅仅是命名几个而已。换句话说,总线在将消息传递到消费者之前就对它进行了控制,也就是 MDB,提供了在传统的 JMS 场景中无法获得的控制级别。
在 WebSphere Application Server V6 中创建 JMS 资源
第一步,我们将在应用程序服务器中创建一些构件:JMS 连接工厂、JMS 队列(MDB 的激活规范)当然还有总线目的地。我们将从总线目的地开始,然后配置 JMS 资源:
- 打开 WebSphere Application Server 管理控制台(服务器必须保持运行)。
- 在左侧的导航面板中选择 Service Integration => Buses。
- 选择 TheBus,然后在下面的对话框中选择 Destinations。
- 当前定义的总线目的地清单展示出来,选择 New。
- 注意您可以创建几种类型的目的地。在我们的例子中,我们将使用 Queue 目的地。选择 Next。
- 进入
PackageReceivedDestination标志符, 然后选择 Next。 - 再次点击 Next 接收总线成员,然后点击 Finish。
- 保存您所作的修改,然后在列表中可以看到新总线,如图 1 所示。
图 1. 总线目的地
- 现在准备创建 JMS 构件。在管理控制台的导航面板中,选择 Resources => JMS Providers => Default Messaging。我们将此作用范围定为 Node,为默认值。图 2 展示了此对话框。
图 2. 默认的消息传递提供者配置
- 创建连接工厂,选择 JMS Connection Factory 链接,然后选 New。在创建对话框中,进入下列各项(图 3):
- 名称:
TheConnectionFactory - JNDI 名称:
jms/TheConncectionFactory - 总线名称:
TheBus
保持其它的默认值,然后点击 OK 保存您所做的修改。
图 3. JMS 连接工厂
- 名称:
- 接下来,在默认的消息传递提供者窗口(图 2)中选择 JMS Queue 链接并点击 New。
- 进入下列各项(图 4):
- 名称:
PackageReceivedQueue - JNDI 名称:
jms/PackageReceivedQueue - 总线名称:
TheBus - 队列名称:
PackageReceivedDestination
保持其它的默认值,然后点击 OK 保存您所做的修改。
图 4. JMS 队列
- 名称:
- 我们需做的最后一件事情是激活规范,它对于 J2EE 1.4 是新的,并且将 MDB 捆绑到队列中。在 MDB 的部署描述符中,您定义激活规范的 JNDI。对于激活规范本身,您确定 MDB 应该监听的队列。返回管理控制台的 Default Messaging Provider 窗口(图 2),选择 JMS activation specification,然后选择 New。
- 输入或选择下列值(图 5):
- 名称:
PackageReceivedActivationSpec - JNDI 名称:
eis/PackageReceivedActivationSpec - 目的地类型:queue
- 目的地 JNDI 名称:
jms/PackageReceivedQueue - 总线名称:TheBus
保持其它的默认值,然后点击 OK 保存您所做的修改。
图 5. JMS 激活规范
- 名称:
这些是我们发送消息到总线和从那儿到消息驱动 bean 需要的所有构件。接下来我们将看一下实际的 Java 代码。
我们不会花费很多时间来描述即将用于本例的代码,因为它同其他任何规范的 JMS 代码真的没有区别(请参阅 JMS 的参考资料部分),而且您能在下载章节中下载我们所使用的代码,包括所需的 J2EE 部署描述符。
发送者主要将发送一个约束传递包的数量的文本消息。因为发送者代码在 J2EE 客户端应用程序中运行,所以我们无法对所用的 JMS 资源的名称进行硬编码。我们使用 java:comp/env namespace 来代替。这两个名称,一个用于连接工厂,一个用于实际队列,在客户端应用程序部署描述符中利用资源引用它们被束缚起来。
这里是客户端代码的摘录:
清单 1
public class Main {
private final static String JMSCF_JNDI_NAME =
"java:comp/env/jms/TheConnectionFactory";
private final static String JMSQ_JNDI_NAME =
"java:comp/env/jms/PackageReceivedQueue";
private final static String messageText =
"Package Received - 24595023";
public static void main(String[] args) throws Exception {
InitialContext initCtx = new InitialContext();
// Finding the WAS QueueConnectionFactory
javax.jms.ConnectionFactory qcf =
(javax.jms.ConnectionFactory) initCtx.lookup(JMSCF_JNDI_NAME);
// Finding the Queue Destination
Destination q = (Destination) initCtx.lookup(JMSQ_JNDI_NAME);
// Create JMS Connection
Connection connection = qcf.createConnection();
// Create JMS Session
Session session =
connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
// Create MessageProducer and TextMessage
MessageProducer queueSender = session.createProducer(q);
TextMessage outMessage = session.createTextMessage();
outMessage.setText(messageText);
// Set type and destination and send
outMessage.setJMSType("package_received");
outMessage.setJMSDestination(q);
queueSender.setDeliveryMode(DeliveryMode.NON_PERSISTENT);
queueSender.send(outMessage);
connection.close();
System.out.println("Send completed");
}
} |
对于 MDB,事情变得更简单了。每一个 MDB 有一个称为 onMessage() 的方法。一旦消息到达 MDB 监听的队列时,这个方法就被调用了。在我们例子中它是这样的:
清单 2.
public void onMessage(javax.jms.Message msg) {
if (!(msg instanceof TextMessage)) {
System.out.println("Received message is not a text message!");
throw new RuntimeException();
}
TextMessage textMsg = (TextMessage)msg;
try {
System.out.println("Received message : "+textMsg.getText());
// forward the received message to business logic for processing...
} catch (JMSException x) {
throw new RuntimeException(x);
}
}
|
客户端应用程序和 MDB 两者都有部署描述符。在这里我们将快速浏览一遍。
客户端部署描述符,在一个称为 application-client.xml 的文件中,包含对用于上述代码中 JMS 连接工厂和队列中 JNDI 名称的引用。如果您在 Application Server Toolkit 中打开客户端部署描述符,它将看起来更加简单,如图 6 所示。
图 6. 客户端部署描述符
在代码中,用到的 Name 值与 java:comp/env 名称空间结合一起。它在代码中用作名为 JMSCF_JNDI_NAME 的变量。WebSphere Bindings 下的输入展示了当它在应用程序服务器被部署时的资源的实际名称(记住我们早先创建的名为 jms/TheConnectionFactory 的 JMS 连接工厂)。
MDB 的部署描述符包含对 JMS 激活规范(它与我们前面创建的 JMS 队列依次联合)的引用,如图 7 所示。
图 7. MDB 部署描述符
我们为该 MDB 定义称为 package_received 的消息选择器,它能更进一步地过滤进来的消息。消息选择器在 JMS 消息的客户端代码上设置:
outMessage.setJMSType("package_received");
我们将客户端和 MDB 模块打包到 EAR 文件中,分别命名为 PackageReceivedClient.ear 和 PackageReceived.ear。在我们运行客户端之前,必须将 MDB 安装并部署到应用程序服务器中。我们接下来就进行操作。
安装和部署 MDB:
- 在管理控制台,在左侧的导航面板选择 Applications => Enterprise Applications。
- 选择 Install。
- 选择 Local file system,进入包含 MDB 的 EAR 文件的名称和目录中,然后选择 Next。
- 确保 Generate Default Bindings 已经核查过并选择 Next。
- 在下面的窗口中,核查 Deploy enterprise beans,然后选择 Next。
- 在接下来的两个对话框中选择 Next,没有任何修改。
- 注意在下面的窗口中,您能重写激活规范的设定值,包括正被使用的 JMS 队列(图 8)。
图 8. 重写激活规范的性能
我们在此不必修改任何东西,但这里展示了在 EAR 文件和部署描述符中应用程序开发者如何调整其设置值。
- 选择 Next,然后是 Finish。当完成部署步骤时,保存您的修改。
- 您的控制台浏览器窗口将看起来如图 9 所示。
图 9. 安装应用程序后的管理控制台
注意新的应用程序已经安装,但并未被启动。要启动它,选择与应用程序相邻的检验栏,然后选择 Start。MDB 现在已经准备从总线接收消息。
- 运行程序客户端发送消息到总线,打开命令提示窗口,改到您正使用的应用程序服务器概要的 \bin 目录下。举个例子,如果您的概要命名为 MyShippingCo 并且您所安装的 WebSphere Application Server 在 c:\WebSphere\AppServer6 目录下,那么 c:\WebSphere\AppServer6\profiles\MyShippingCo\bin 将是您所需要的目录。
- 通过调用 setupcmdline 实用程序设置合适的环境。
- 现在,通过调用 launchclient 实用程序来开启客户端应用程序,传递客户端 EAR 文件作为参数,如图 10 所示。
图 10. 开启 launchclient 实用程序
- 在 \logs\server1 目录下检查 SystemOut.log 文件。这是 MDB 输出的地方,而且它将展示图 11 中打印的消息。
图 11. SystemOut.log 文件
输出的日志文件将包含有用的信息以防出现问题,因此检查它通常是一个很好的做法。
在本文中,我们描述了用 WebSphere Application Server V6 Messaging Resources 构建企业服务总线的通用场景。无论何时传递包,我们构建的服务器都会向总线发送确认消息,使用 JMS 作为与总线通信的协议。消息的接收者是消息驱动 bean,也使用 JMS 作为它的协议。
在以后的文章中,我们将向您展示当消息从总线中经过时,如何利用中介进行操作。因此请耐心等待。
| 名字 | 大小 | 下载方法 |
|---|---|---|
| PackageReceived.ZIP | 8 KB | FTP |
- 您可以参阅本文在 developerWorks 全球站点上的 英文原文。
-
使用 WebSphere Application Server V6 构建企业服务总线:第 1 部分.WebSphere V6 Messaging Resources 介绍
-
使用 WebSphere Application Server V6 构建企业服务总线:第 2 部分.企业需求和总线
-
来自 Sun 的 JMS 技术期刊
-
developerWorks 上的 JMS 技术期刊
-
JMS 1.1 API 介绍
-
企业服务总线的 IBM Web 地址
-
SOA 和 Web 服务的 Web 地址
-
服务数据对象的引用集合
-
红皮书:模式:面向服务的架构和 Web 服务
-
红皮书:模式:利用企业服务总线实现 SOA
-
红皮书:模式:Using Business Service Choreography In Conjunction With An Enterprise Service Bus
-
参考资料:WebSphere Application Server Version 6.0 信息中心
-
红皮书:WebSphere Application Server V6 技术概览
- 通过参加 developerWorks blogs 而进入 developerWorks 社区。
- 购买打折的 Web 服务书籍。