Spring JMS MappingJackson2MessageConverter-无法处理错误

问题描述

我将Spring JMS与ActiveMQ结合使用,并且我使用MappingJackson2MessageConverter在各个组件之间传递消息。

我的核心问题是,当MappingJackson2MessageConverter遇到内部反序列化错误时,将字符串反序列化为某些对象时,不会以任何我可以响应的方式引发这些异常。我的错误处理程序逻辑从未被调用,也没有抛出任何我可以访问的异常。这些反序列化错误似乎已完全被吞没,并且在控制台中记录了这些反序列化错误后,我没有机会执行响应它们的自定义逻辑。

我按如下方式定义MappingJackson2MessageConverter bean:

  @Bean
  public MessageConverter jacksonJmsMessageConverter() {
    MappingJackson2MessageConverter converter = new MappingJackson2MessageConverter();
    converter.settargettype(MessageType.TEXT);
    converter.setTypeIdPropertyName("_type");
    return converter;
  }

我定义了一个JMS侦听器工厂,如下所示:

  @Bean
  public JmsListenerContainerFactory<?> jmsListenerQueueFactory(ConnectionFactory connectionFactory,DefaultJmsListenerContainerFactoryConfigurer configurer,JmsErrorHandler jmsErrorHandler) {
    DefaultJmsListenerContainerFactory factory = new DefaultJmsListenerContainerFactory();
    factory.setErrorHandler(jmsErrorHandler); // <-- I expect this to be used
    configurer.configure(factory,connectionFactory);

    return factory;
  }

上一行中最重要的是setErrorHandler调用。我定义了一个简单的ErrorHandler对象,试图捕获我的@JmsListener方法可能引发的错误。这个简单的错误处理程序如下所示:

  public class JmsErrorHandler implements ErrorHandler {

  @Override
  public void handleError(Throwable t) {
    System.out.println("WE HAVE THE ERROR!");
  }
}

我的侦听器也很简单,如下所示:

  @JmsListener(id = MY_ID,destination = MY_DEST)
  public void processMessage(MyPojoMessage myPojoMessage) {
     // This code is obvIoUsly never reached,since the serialization error occurs. 

总体而言,这是一个非常简单且基本的设置。现在,当我发送无效消息时,Jackson将失败进行解析,我在控制台中收到以下错误

19-10-2020 09:05:33.933 [35m[DefaultMessageListenerContainer-1][0;39m [31mWARN [0;39m o.s.j.l.DefaultMessageListenerContainer.invokeErrorHandler - Execution of JMS message listener Failed,and no ErrorHandler has been set.

org.springframework.jms.listener.adapter.ListenerExecutionFailedException: Listener method 'public void com.example.processMessage(com.example.MyPojoMessage)' threw exception; nested exception is org.springframework.jms.support.converter.MessageConversionException: Failed to convert JSON message content; nested exception is com.fasterxml.jackson.databind.JsonMappingException

此异常是可以预期的-因为我提供了杰克逊无法序列化的无效负载。但是,对于我来说,似乎没有办法代码配置为以我可以响应的方式实际捕获此异常。我在上面的代码中设置错误处理程序。然而日志却抱怨no ErrorHandler has been set似乎是错误的。

我没有其他方法可以引用此Jackson内部异常。有什么办法吗?

解决方法

好像ConditionalOnMissingBean自动配置在bean name

所以你应该有这样的东西。

@Bean
  public JmsListenerContainerFactory<?> jmsListenerContainerFactory(ConnectionFactory connectionFactory,DefaultJmsListenerContainerFactoryConfigurer configurer,JmsErrorHandler jmsErrorHandler) {
    DefaultJmsListenerContainerFactory factory = new DefaultJmsListenerContainerFactory();
    factory.setErrorHandler(jmsErrorHandler); // <-- I expect this to be used
    configurer.configure(factory,connectionFactory);
    return factory;
  }