在 OpenEJB 中部署具有多个队列名称的 MDB 时出错

发布于 2024-09-30 01:03:08 字数 2962 浏览 0 评论 0原文

升级到 OpenEJB 3.1.3 后,Tomcat/OpenEJB 启动时出现以下错误:

ERROR - Unable to register MBean 
java.lang.IllegalStateException: javax.management.MalformedObjectNameException: Invalid character ',' in key part of property
    at org.apache.openejb.monitoring.ObjectNameBuilder.build(ObjectNameBuilder.java:59)
    at org.apache.openejb.core.mdb.MdbContainer.deploy(MdbContainer.java:169)
    at org.apache.openejb.assembler.classic.Assembler.createApplication(Assembler.java:599)
    at org.apache.openejb.assembler.classic.Assembler.createApplication(Assembler.java:450)
    at org.apache.openejb.assembler.classic.Assembler.buildContainerSystem(Assembler.java:368)
    at org.apache.openejb.assembler.classic.Assembler.build(Assembler.java:280)
    at org.apache.openejb.OpenEJB$Instance.<init>(OpenEJB.java:125)
    at org.apache.openejb.OpenEJB$Instance.<init>(OpenEJB.java:60)
    at org.apache.openejb.OpenEJB.init(OpenEJB.java:271)
    at org.apache.openejb.OpenEJB.init(OpenEJB.java:250)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.apache.openejb.loader.OpenEJBInstance.init(OpenEJBInstance.java:36)
    at org.apache.openejb.client.LocalInitialContextFactory.init(LocalInitialContextFactory.java:71)
    at org.apache.openejb.client.LocalInitialContextFactory.init(LocalInitialContextFactory.java:53)
    at org.apache.openejb.client.LocalInitialContextFactory.getInitialContext(LocalInitialContextFactory.java:42)
    ... 
    <proprietary stack trace skipped>
    ...
Caused by: javax.management.MalformedObjectNameException: Invalid character ',' in key part of property
    at javax.management.ObjectName.construct(ObjectName.java:535)
    at javax.management.ObjectName.<init>(ObjectName.java:1403)
    at org.apache.openejb.monitoring.ObjectNameBuilder.build(ObjectNameBuilder.java:57)
    ... 70 more
INFO - Created Ejb(deployment-id=InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT, ejb-name=InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT, container=My MDB Container )

以下 MDB 导致此错误:

@MessageDriven(name="InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")
public class InboundXMLQueueHandler implements MessageListener {
...

因为更改为错误后就

@MessageDriven(name="InboundXMLQueueHandlerST")
public class InboundXMLQueueHandler implements MessageListener {
...

消失了。

正如您所看到的,我们在注释中使用单个类和逗号分隔的队列名称定义了两个侦听器。这在 3.1.2 中工作得很好(至少看起来是这样),但现在它给了我们上面的错误(尽管该错误似乎并没有阻止 MDB 的部署,但 JMX 监控对我们来说至关重要)。

我也无法找到任何使用 @MessageDriven 注释与多个队列(单个 MDB 类,多个逗号分隔的队列名称)的示例。这是一个错误的做法吗?它是已记录的功能吗? 3.1.3 中发生了什么变化导致 JMX 无法再注册 MDB?

The following error appeared at Tomcat/OpenEJB startup after upgrading to OpenEJB 3.1.3:

ERROR - Unable to register MBean 
java.lang.IllegalStateException: javax.management.MalformedObjectNameException: Invalid character ',' in key part of property
    at org.apache.openejb.monitoring.ObjectNameBuilder.build(ObjectNameBuilder.java:59)
    at org.apache.openejb.core.mdb.MdbContainer.deploy(MdbContainer.java:169)
    at org.apache.openejb.assembler.classic.Assembler.createApplication(Assembler.java:599)
    at org.apache.openejb.assembler.classic.Assembler.createApplication(Assembler.java:450)
    at org.apache.openejb.assembler.classic.Assembler.buildContainerSystem(Assembler.java:368)
    at org.apache.openejb.assembler.classic.Assembler.build(Assembler.java:280)
    at org.apache.openejb.OpenEJB$Instance.<init>(OpenEJB.java:125)
    at org.apache.openejb.OpenEJB$Instance.<init>(OpenEJB.java:60)
    at org.apache.openejb.OpenEJB.init(OpenEJB.java:271)
    at org.apache.openejb.OpenEJB.init(OpenEJB.java:250)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.apache.openejb.loader.OpenEJBInstance.init(OpenEJBInstance.java:36)
    at org.apache.openejb.client.LocalInitialContextFactory.init(LocalInitialContextFactory.java:71)
    at org.apache.openejb.client.LocalInitialContextFactory.init(LocalInitialContextFactory.java:53)
    at org.apache.openejb.client.LocalInitialContextFactory.getInitialContext(LocalInitialContextFactory.java:42)
    ... 
    <proprietary stack trace skipped>
    ...
Caused by: javax.management.MalformedObjectNameException: Invalid character ',' in key part of property
    at javax.management.ObjectName.construct(ObjectName.java:535)
    at javax.management.ObjectName.<init>(ObjectName.java:1403)
    at org.apache.openejb.monitoring.ObjectNameBuilder.build(ObjectNameBuilder.java:57)
    ... 70 more
INFO - Created Ejb(deployment-id=InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT, ejb-name=InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT, container=My MDB Container )

The following MDB causes this error:

@MessageDriven(name="InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")
public class InboundXMLQueueHandler implements MessageListener {
...

because after changing to

@MessageDriven(name="InboundXMLQueueHandlerST")
public class InboundXMLQueueHandler implements MessageListener {
...

error is gone.

As you can see we define two listeners using single class and comma-separated queue names in annotations. This worked flawlessly with 3.1.2 (at least it seemed) but now it gives us the error above (though the error doesn't seem to prevent the deployment of MDBs but JMX monitoring is critical to us).

I am unable to find any example of usage @MessageDriven annotation with multiple queues (single MDB class, multiple comma-separated queue names) anymore either. Is this a wrong way do it? Is it a documented feature? What changed in 3.1.3 so that JMX can't register MDB anymore?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

仙女山的月亮 2024-10-07 01:03:08

嗯,我们在 3.1.2 中没有 JMX 支持。我个人从未尝试过将 MDB 连接到两个队列 - 有点惊讶它竟然有效。 ActiveMQ 负责实际的“队列连接”(JMS 连接器的标准工作),我们只是传递元数据。

在 OpenEJB 方面,我们所做的唯一魔法是尝试通过 @ActivationConfigProperty 填写您的 destinationdestinationType 设置(如果您还没有)这样做了。如果未填写,我们会将 destination 设置为您的 Bean 名称;如果未填写,我们会将 destinationType 设置为 javax.jms.Queue未填写。

因此,如果所有内容均已显式设置,那么上面的 bean 基本上将如下所示。

@MessageDriven(
    name="InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT",
    activationConfig = {
        @ActivationConfigProperty(
           propertyName = "destinationType", 
           propertyValue = "javax.jms.Queue"),
        @ActivationConfigProperty(
           propertyName = "destination", 
           propertyValue = "InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")})
public class InboundXMLQueueHandler implements MessageListener {
...

假设 ActiveMQ 实际上为您提供了两个队列,这就是激活配置。

也许最简单的尝试就是显式设置目标名称并删除 bean 名称。

@MessageDriven(
    activationConfig = {
        @ActivationConfigProperty(
           propertyName = "destination", 
           propertyValue = "InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")})
public class InboundXMLQueueHandler implements MessageListener {
...

Hmm, we didn't have JMX support in 3.1.2. I've personally never tried hooking an MDB up to two queues -- sort of surprised that worked. It's ActiveMQ that does the actual "queue hooking up" (standards job of the JMS connector), we just pass the meta-data over.

On the OpenEJB side, the only magic that we do is attempt to fill in your destination and destinationType settings via @ActivationConfigProperty if you haven't done so. We'll set destination to your bean name if that isn't filled in and we will set destinationType to javax.jms.Queue if that isn't filled in.

So your bean above would essentially look like this if all was set explicitly.

@MessageDriven(
    name="InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT",
    activationConfig = {
        @ActivationConfigProperty(
           propertyName = "destinationType", 
           propertyValue = "javax.jms.Queue"),
        @ActivationConfigProperty(
           propertyName = "destination", 
           propertyValue = "InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")})
public class InboundXMLQueueHandler implements MessageListener {
...

Assuming ActiveMQ actually was giving you both queues, this is the activationConfig that would do it.

Probably the simplest thing to try is to explicitly set the destination name and just delete the bean name.

@MessageDriven(
    activationConfig = {
        @ActivationConfigProperty(
           propertyName = "destination", 
           propertyValue = "InboundXMLQueueHandlerST,InboundXMLQueueHandlerMT")})
public class InboundXMLQueueHandler implements MessageListener {
...
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文