Java 如何避免在出现意外错误时关闭SimpleMessageListenerContainer?

Java 如何避免在出现意外错误时关闭SimpleMessageListenerContainer?,java,spring,spring-boot,spring-rabbit,Java,Spring,Spring Boot,Spring Rabbit,我使用Java boot 1.4.0和“spring boot starter amqp”连接到rabbitMq。消息生产者、消费者和rabbitMq服务器都在我的控制之下。在几个月的生产过程中,一切正常。但突然,我的消费者停止了,下面给出了例外情况。由于我只生成始终有效的消息,所以我不知道哪里出错了 但这导致我的侦听器容器关闭。因此,我的消息处理停止了。我不得不手动重新启动我的消息消费者程序 所以我的问题是: 我们能否避免在任何意外情况下完全关闭侦听器容器 是否可以优雅地丢弃此类消息并保持侦听

我使用Java boot 1.4.0和“spring boot starter amqp”连接到rabbitMq。消息生产者、消费者和rabbitMq服务器都在我的控制之下。在几个月的生产过程中,一切正常。但突然,我的消费者停止了,下面给出了例外情况。由于我只生成始终有效的消息,所以我不知道哪里出错了

但这导致我的侦听器容器关闭。因此,我的消息处理停止了。我不得不手动重新启动我的消息消费者程序

所以我的问题是:

  • 我们能否避免在任何意外情况下完全关闭侦听器容器
  • 是否可以优雅地丢弃此类消息并保持侦听器容器的活动状态
  • 如果没有,那么有没有办法检查我所有的侦听器容器是否都在运行,并在发现它们已死亡时启动它们?(注意:我查看了RabbitListenerEndpointRegistry.getListenerContainers()。但它似乎不包括SimpleMessageListenerContainer容器。)
  • 异常日志:

    2017-02-20 12:42:18.441错误18014---[writeToDBQQueueListenerContainer-17]o.s.a.r.l.SimpleMessageListenerContainer:使用者线程错误,线程中止。
    java.lang.NoClassDefFoundError:org/springframework/messaging/handler/annotation/support/MethodArgumentNotValidException
    在org.springframework.amqp.rabbit.listener.ConditionalRejectingErrorHandler$DefaultExceptionStrategy.causeIsFatal(ConditionalRejectingErrorHandler.java:110)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.ConditionalRejectingErrorHandler$DefaultExceptionStrategy.isFatal(ConditionalRejectingErrorHandler.java:97)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.ConditionalRejectingErrorHandler.handleError(ConditionalRejectingErrorHandler.java:72)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.invokeErrorHandler(AbstractMessageListenerContainer.java:625)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.handleListenerException(AbstractMessageListenerContainer.java:852)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.AbstractMessageListenerContainer.executeListener(AbstractMessageListenerContainer.java:685)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.doReceiveAndExecute(SimpleMessageListenerContainer.java:1165)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.receiveAndExecute(SimpleMessageListenerContainer.java:1149)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer.access$1100(SimpleMessageListenerContainer.java:95)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在org.springframework.amqp.rabbit.listener.SimpleMessageListenerContainer$AsyncMessageProcessingConsumer.run(SimpleMessageListenerContainer.java:1312)~[spring-rabbit-1.6.1.RELEASE.jar!/:na]
    在java.lang.Thread.run(Thread.java:745)[na:1.8.091]
    原因:java.lang.ClassNotFoundException:org.springframework.messaging.handler.annotation.support.MethodArgumentNotValidException
    在java.net.URLClassLoader.findClass(URLClassLoader.java:381)~[na:1.8.091]
    在java.lang.ClassLoader.loadClass(ClassLoader.java:424)~[na:1.8.091]
    在org.springframework.boot.loader.LaunchedURLClassLoader.loadClass(LaunchedURLClassLoader.java:89)~[KattaQueueManager-0.0.1-SNAPSHOT.jar:0.0.1-SNAPSHOT]
    在java.lang.ClassLoader.loadClass(ClassLoader.java:357)~[na:1.8.091]
    
    ... 11个常见的框架省略了
    几个月前我也遇到了同样的问题,这对我很有帮助。 如果Rabbit Java客户端的版本在4.0.0之前,您没有自动恢复连接,则需要设置,如下所示:

    ConnectionFactory factory = new ConnectionFactory();
    factory.setUsername(userName);
    factory.setPassword(password);
    factory.setVirtualHost(virtualHost);
    factory.setHost(hostName);
    factory.setPort(portNumber);
    
    // connection that will recover automatically
    factory.setAutomaticRecoveryEnabled(true);
    
    // attempt recovery every 10 seconds
    factory.setNetworkRecoveryInterval(10000);
    
    Connection conn = factory.newConnection();
    
    尝试检查RabbitMQ的文档:

    从堆栈跟踪来看,类路径中似乎缺少几个类/jar,请检查它们是否存在/包含在类路径中感谢您的评论,Bond。这是一个完整的工作设置,在生产上运行了几个月。肯定所有需要的组件/罐子都准备好了。好的。。您在日志中是否看到任何
    异常InInitializeRerror
    ?没有。这只发生在一条输入消息中。因此,我想知道如何避免在这种不可预见的情况下关闭侦听器容器。你找到解决办法了吗?谢谢@Brother。我使用的是spring boot 1.4.0版本中的“spring boot starter amqp”。据我所知,默认情况下,它具有主要的重新连接功能,能够处理基本的连接断开。因此,在这方面基本上没有更多配置。