IBM Websphere MQ - Tomcat 部署的 EJB 和 MDB 迁移

IBM Websphere MQ - EJB and MDB migration for Tomcat deployment

我已经为此苦苦挣扎了很长时间。我有一个 IBM Websphere MQ,它使用 EJB 和 MDB

下面是配置ejb mdb的地方

<?xml version="1.0" encoding="UTF-8"?>
<ejb-jar-bnd xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://websphere.ibm.com/xml/ns/javaee"
    xsi:schemaLocation="http://websphere.ibm.com/xml/ns/javaee http://websphere.ibm.com/xml/ns/javaee/ibm-ejb-jar-bnd_1_0.xsd" version="1.0">
  <message-driven name="Queue1MDB">
    <jca-adapter activation-spec-binding-name="jms/Queue1MQActivationSpec" destination-binding-name="jms/Queue1RequestQueue"/>
    <resource-ref binding-name="jms/QueueConnectionFactory" name="jms/QueueConnectionFactory"/>
    <message-destination-ref binding-name="jms/SuccessfulResponseQueue" name="jms/SuccessfulResponseQueue"/>
    <message-destination-ref binding-name="jms/FailedResponseQueue" name="jms/FailedResponseQueue"/>
  </message-driven>

  <message-driven name="Queue2MDB">
    <jca-adapter activation-spec-binding-name="jms/Queue2MQActivationSpec" destination-binding-name="jms/Queue2RequestQueue"/>
    <resource-ref binding-name="jms/QueueConnectionFactory" name="jms/QueueConnectionFactory"/>
    <message-destination-ref binding-name="jms/SuccessfulResponseQueue" name="jms/SuccessfulResponseQueue"/>
    <message-destination-ref binding-name="jms/FailedResponseQueue" name="jms/FailedResponseQueue"/>
  </message-driven>

  <message-driven name="Queue3MDB">
    <jca-adapter activation-spec-binding-name="jms/Queue3MQActivationSpec" destination-binding-name="jms/Queue3RequestQueue"/>
    <resource-ref binding-name="jms/QueueConnectionFactory" name="jms/QueueConnectionFactory"/>
    <message-destination-ref binding-name="jms/SuccessfulResponseQueue" name="jms/SuccessfulResponseQueue"/>
    <message-destination-ref binding-name="jms/FailedResponseQueue" name="jms/FailedResponseQueue"/>
  </message-driven>

  <message-driven name="Queue4MDB">
    <jca-adapter activation-spec-binding-name="jms/Queue4MQActivationSpec" destination-binding-name="jms/Queue4RequestQueue"/>
    <resource-ref binding-name="jms/QueueConnectionFactory" name="jms/QueueConnectionFactory"/>
    <message-destination-ref binding-name="jms/SuccessfulResponseQueue" name="jms/SuccessfulResponseQueue"/>
    <message-destination-ref binding-name="jms/FailedResponseQueue" name="jms/FailedResponseQueue"/>
  </message-driven>
</ejb-jar-bnd>

这是在ear中配置的,部署在IBM WAS中。 destination-binding-name 将从 IBM WAS 中选择相应的队列详细信息。

后来,我在 java class 中配置 MDB,如下所示,同时在所有队列上实现侦听并提取消息:

@Resource(name = "jms/QueueContractConnectionFactory")
private ConnectionFactory connectionFactory;

@Resource(name = "jms/FailedResponseQueue")
private Queue errorQueue;

@Resource(name = "jms/SuccessfulResponseQueue")
private Queue responseQueue;

我现在必须删除 ejb 并修改 mdb 配置以使其在 tomcat 中可部署。

xml 是个东西,我真的不知道如何在没有 ejb 参数的情况下映射它。

有人可以帮助或分享有关如何实现此目标的文档吗?我想要一个 IBM MQ 到 Spring JMS with Activation Spec 的例子。

提前致谢。

如评论所述,这不仅仅是用 Tomcat 替换 WAS 的问题,因为它们不是同一种容器。因此,您不能直接将 WAS 工件(尤其是 MDB)直接部署到 Tomcat。为了让这些进入 Tomcat,它们必须被重写。

作为 MDB,容器为您管理:连接到 JMS 服务器,将消息从 queue/topic 路由到您的逻辑,multi-threaded 消息处理(处理多个排队的消息一次),最值得注意的是事务管理。

现在,针对 JMS 的消息处理非常简单。您可以很容易地连接到 JMS。您可以从网上复制一个示例并使其正常工作。 运行 后台处理很简单,也有这样的例子。 JMS 2.0 比 JMS 1.x 更易于使用。没有理由不移植到那个(除非 MQ 不支持 JMS 2.0)。

运行 逻辑的多个实例在事务上并不是那么简单,但也许这不是您处理的一个重要方面。

但是,即使您能够使所有这些工作正常进行,此时也不能保证您的逻辑会直接工作。我们不知道您的逻辑是否调用其他 EJB 或利用任何其他 Java EE 基础结构。如果这样做,您还必须移植逻辑的那个方面,而不仅仅是 MDB 连接。

所以,这是一个更深层次的问题。说起来容易 "just deploy it in Tomcat",但可能有一些细节会破坏它并需要加以考虑。

另一种方法是将逻辑转换为 Spring,因为它可以很容易地部署在 Tomcat 中。但这并不一定比其他任何事情都简单——所有注意事项仍然存在。

最后,"deploying in Tomcat" 在这种情况下几乎是 non-sequitur,因为 MDB 不是 Web 应用程序,而 Tomcat 部署 Web 应用程序。您可以创建一个 shell 的 Web 应用程序,它只执行您的消息驱动逻辑。这很容易做到,我和其他许多人都滥用 Web 应用程序生命周期来达到我们自己邪恶的目的。

所以,最后,我认为您需要更清楚地了解 "deploy in Tomcat" 的真正含义,最终的期望是什么,以及您的消息逻辑是否依赖于其他 Java EE基础设施等。目标是在 Tomcat 中 运行 还是在 WAS 中不 运行 (在这种情况下,如评论中所述,您可能会使用其他应用服务器更容易过渡到)。

关于 Websphere MQ,您应该了解一件事。仅通过 Websphere 应用程序服务器支持 JMS 的 MQ 类 连接池。当您迁移到 Tomcat 时,您可能会遇到性能下降并且您可能必须自己实施一些池化。我认为 spring 在这方面可以提供帮助。我将从 IBM 文档中引用它

public void setUseConnectionPooling(boolean usePooling)

Deprecated. JMS does not use connection pooling anymore. Any connection pooling should be done using the facilities provided by the App Server. Set the use of ConnectionPooling in earlier versions of the IBM MQ classes for JMS. This method is retained for compatibility with older MQJMS applications, but, because this Connection Pooling functionality has been removed from version 7, setting this property will have no effect.

https://www.ibm.com/support/knowledgecenter/en/SSFKSJ_9.0.0/com.ibm.mq.javadoc.doc/WMQJMSClasses/com/ibm/mq/jms/MQConnectionFactory.html#setUseConnectionPooling-boolean-

我认为你最好的办法是 spring-ify(移动到 spring)你的 WAS 应用程序,然后切换到 Tomcat。一旦你移动到 spring,切换应该是小菜一碟。它应该是独立于容器的。网上有很多关于如何将 Java EE 迁移到 spring 应用程序的食谱。这个练习已经做了很多年了(因为 spring 存在:).

在此过程中,您还可以分而治之,最终得到多个应用程序,而不是单一应用程序。

迈克我的另一个 post 您链接到此问题概述了假设您擅长设置 spring 框架、MQ 和服务器管理的步骤。但是,如果您正在为入门而苦苦挣扎,这里有一些建议。

开始之前,您需要了解这在技术上具有挑战性。有时,与其改变现有的东西,不如将现有的东西分解成多个模块并从头开始实施它们更有意义。如果您选择更改现有内容,请按以下方法处理:

让 spring 框架在您使用 RAD 构建的应用程序中运行。你这样做成功了吗?只需从应用程序上下文中注入任何 bean,看看是否可以让它在 WAS 上工作。如果你能成功做到这一点,就意味着你抢先一步,剩下的就可以完成了。当您到达这里时请告诉我 - 将您的应用程序上下文或配置粘贴到此处。我可以告诉你下一步该怎么做。请记住,您不必立即切换到 tomcat - 您的目标应该是用可以收听消息的 spring bean 替换 MDB - 这可以 运行 在 WAS 上.