DefaultMessageListenerContainer是否停止,关闭关闭数据库连接?

发布于 2025-01-26 10:26:32 字数 3315 浏览 3 评论 0原文

我有一个defaultmessagelistenercontainer,正在从队列中处理一条消息。

在处理该消息时 - 停止,在DefaultMessageListenerContainer上调用了关闭方法。这个关闭的数据库连接吗?

看起来它正在关闭数据库连接,因此正在处理的消息被完全处理中断。

我看到以下错误:

osjdbc.support.sqlerrorcodesfactory:提取数据库名称时错误 封闭连接;嵌套例外是Java.sql.sqlrecoverableException:封闭的连接

可能是因为停止并关闭了DefaultMessageListenerContainer?


我的代码如下。 StartStopContainer是我试图停止和关闭容器的地方。我只想在侦听器完成当前消息时关闭容器。我添加了逻辑以找出侦听器是否完成处理。

是以下逻辑是唯一的方法,还是有更好的方法来确定听众是否完成处理。请建议。谢谢。

public class MyMessageConsumerFacade {
    
    private ConnectionFactory connectionFactory() {
        ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory();
        connectionFactory.setBrokerURL(url);
        connectionFactory.setUserName(userName);
        connectionFactory.setPassword(password);

        return connectionFactory;
    }

    @Bean
    public MessageListenerContainer listenerContainer() {
        
        DefaultMessageListenerContainer container = new DefaultMessageListenerContainer();
        container.setConnectionFactory(connectionFactory());
        container.setDestinationName(queueName);
        container.setMessageListener(new MyJmsListener());      
        return container;
    }
}

public class MyJmsListener implements MessageListener { 
  public boolean onMessageCompleted; 
  public void onMessage(Message message) { 
     onMessageCompleted = false; 
     processMessage(message); 
     onMessageCompleted = true; 
  } 
} 

private String startStopContainer(ExecutionContext etk)  {
        String response = "success";
        
        AnnotationConfigApplicationContext context = null;
        DefaultMessageListenerContainer myNewContainer = null;
        
        if (context == null) {
            context = new AnnotationConfigApplicationContext(MyMessageConsumerFacade.class);
        }   

        if (myNewContainer == null) {
            myNewContainer = context.getBean(DefaultMessageListenerContainer.class);
        }

        MyCaseMessageJmsListener messageJmsListener = (MyCaseMessageJmsListener) myNewContainer.getMessageListener();
        

        if (!myNewContainer.isRunning()) {// container not running
            myNewContainer.start();
        }
        
        //due to some business logic we need to stop listener every 5 minutes, so sleep for 5 minutes and then stop
        try {
            Thread.sleep(300000);
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
                                
        if (myNewContainer.isRunning()) {
            myNewContainer.stop();
            
        }
        
        //Before shutting down container , make sure listener processed all msgs completely
        if(!messageJmsListener.isOnMessageCompleted) {      
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
        if(messageJmsListener.isOnMessageCompleted) {
            myNewContainer.shutdown();
        }
        
        if (context != null) {
            context.destroy();          
        }
        
        return response;
    }    

有比这更好的方法吗?

I have a DefaultMessageListenerContainer which is processing a message from the queue.

While the message is being processed -- stop , shutdown methods are called on DefaultMessageListenerContainer. Does this close database connections?

Looks like it is closing the database connections and hence the message being processed is getting interrupted from completely processing.

I see these errors :

o.s.jdbc.support.SQLErrorCodesFactory : Error while extracting database name
Closed Connection; nested exception is java.sql.SQLRecoverableException: Closed Connection

could these be because the DefaultMessageListenerContainer was stopped and shutdown ?


My code is as follows . startStopContainer is where I am trying to stop and shutdown container. I want to shutdown container only if listener completed processing the current message. I added logic to figure out if listener completed processing .

Is the below logic the only way or is there a better way to figure out if listener completed processing. Please suggest. Thank you.

public class MyMessageConsumerFacade {
    
    private ConnectionFactory connectionFactory() {
        ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory();
        connectionFactory.setBrokerURL(url);
        connectionFactory.setUserName(userName);
        connectionFactory.setPassword(password);

        return connectionFactory;
    }

    @Bean
    public MessageListenerContainer listenerContainer() {
        
        DefaultMessageListenerContainer container = new DefaultMessageListenerContainer();
        container.setConnectionFactory(connectionFactory());
        container.setDestinationName(queueName);
        container.setMessageListener(new MyJmsListener());      
        return container;
    }
}

public class MyJmsListener implements MessageListener { 
  public boolean onMessageCompleted; 
  public void onMessage(Message message) { 
     onMessageCompleted = false; 
     processMessage(message); 
     onMessageCompleted = true; 
  } 
} 

private String startStopContainer(ExecutionContext etk)  {
        String response = "success";
        
        AnnotationConfigApplicationContext context = null;
        DefaultMessageListenerContainer myNewContainer = null;
        
        if (context == null) {
            context = new AnnotationConfigApplicationContext(MyMessageConsumerFacade.class);
        }   

        if (myNewContainer == null) {
            myNewContainer = context.getBean(DefaultMessageListenerContainer.class);
        }

        MyCaseMessageJmsListener messageJmsListener = (MyCaseMessageJmsListener) myNewContainer.getMessageListener();
        

        if (!myNewContainer.isRunning()) {// container not running
            myNewContainer.start();
        }
        
        //due to some business logic we need to stop listener every 5 minutes, so sleep for 5 minutes and then stop
        try {
            Thread.sleep(300000);
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
                                
        if (myNewContainer.isRunning()) {
            myNewContainer.stop();
            
        }
        
        //Before shutting down container , make sure listener processed all msgs completely
        if(!messageJmsListener.isOnMessageCompleted) {      
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
        if(messageJmsListener.isOnMessageCompleted) {
            myNewContainer.shutdown();
        }
        
        if (context != null) {
            context.destroy();          
        }
        
        return response;
    }    

Is there a better way than this?

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

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

发布评论

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

评论(1

忆沫 2025-02-02 10:26:32

不;该容器对JDBC或与此连接的任何连接一无所知。

停止容器只能阻止JMS消费者接收消息; 关闭()在容器上关闭消费者。

其他东西正在关闭您的JDBC连接。

No; the container knows nothing about JDBC or any connections thereto.

Stopping the container only stops the JMS consumer(s) the consumers from receiving messages; shutDown() on the container closes the consumer(s).

Something else is closing your JDBC connection.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文