停止 Spring JMS 侦听器会导致 ActiveMQ Classic 上出现奇怪的行为

问题描述 投票:0回答:1

在启动和停止 JMS 侦听器时,我遇到了一些奇怪的行为。我已经像这样定义了两个侦听器:

@JmsListener(id="myid", destination = "myDestination")
public void SampleJmsListenerMethod(String text) {
    System.out.println("1: "+text);
}

@JmsListener(id="myid2", destination = "myDestination")
public void SampleJmsListenerMethod2(String text) {
    System.out.println("2: "+text);
}

使用 REST 控制器,我可以启动和停止其中一个:

@RequestMapping(value="/halt", method= RequestMethod.GET)
public @ResponseBody
String haltJmsListener() {
    JmsListenerEndpointRegistry customRegistry =
            context.getBean(JmsListenerEndpointRegistry.class);
    Objects.requireNonNull(customRegistry.getListenerContainer("myid")).stop();
    return "Jms Listener Stopped";
}

@RequestMapping(value="/restart", method=RequestMethod.GET)
public @ResponseBody
String reStartJmsListener() {
    JmsListenerEndpointRegistry customRegistry =
            context.getBean(JmsListenerEndpointRegistry.class);
    Objects.requireNonNull(customRegistry.getListenerContainer("myid")).start();
    return "Jms Listener restarted";
}

当应用程序启动时,我看到两个连接和两个活跃的消费者。控制台的输出是:

Sending message to 'myDestination' destination with text hello
1: hello
Sending message to 'myDestination' destination with text hello
2: hello
Sending message to 'myDestination' destination with text hello
1: hello
Sending message to 'myDestination' destination with text hello
2: hello

如果我停止一个监听器,我仍然看到两个连接和两个消费者,但输出突然是:

Sending message to 'myDestination' destination with text hello
Sending message to 'myDestination' destination with text hello
2: hello
Sending message to 'myDestination' destination with text hello
Sending message to 'myDestination' destination with text hello
2: hello

所以我只收到每条消息。其他消息保留在队列中。如果我然后重新启动侦听器,我会得到

1: hello
1: hello
Sending message to 'myDestination' destination with text hello
1: hello
Sending message to 'myDestination' destination with text hello
2: hello
Sending message to 'myDestination' destination with text hello
1: hello

首先是两条消息,已发送但未消费。然后我恢复正常,消息由两个侦听器中的一个循环消耗。

我已经使用 ActiveMQ Classic 5.15 (Spring 2.3.12) 和 5.16 (Spring 2.7.8) 对此进行了测试,并且都表现出了这种行为。

如果我在 Spring 3.2.1 和 5.18 中执行此操作,我不会看到此行为。如果我停止侦听器,所有消息都将进入剩余的侦听器,并且连接将被删除。

有谁知道它是否应该这样工作?

activemq spring-jms
1个回答
0
投票

旧版本似乎停止了侦听器,但不释放连接。另请参阅对此答案的评论:https://stackoverflow.com/a/57993175/900119

这解释了我注意到的行为。似乎较新的版本也释放了连接,从而允许 ActiveMQ 将消息重定向到其他消费者。

目前我已经解决了这个问题,不使用 messagelistenercontainer,而仅使用 connectionfactory 并手动创建连接、会话和消息消费者。我可以再次关闭它们,从而产生所需的行为。

PS。 Spring 似乎也有一张票来改变这种行为:https://github.com/spring-projects/spring-framework/issues/30612

© www.soinside.com 2019 - 2024. All rights reserved.