Spring Integration测试:如何捕获错误通道的异常消息?
问题描述
我正在编写Spring Integration测试,验证错误通道能否从流程通道接收消息。
通道配置代码:
@Bean(START_PROCESSING_CHANNEL) MessageChannel processingStart() { return new DirectChannel(); } @Bean(CUSTOM_ERROR_CHANNEL) MessageChannel channelError() { return new DirectChannel(); }
业务代码运行正常,但测试编写遇到问题:向processingStart通道发送消息后,拦截器工作正常,但要么收到来自buildErrorStartMessage()的带头部的负载,要么添加标注(*)的代码后测试失败。测试代码如下:
when(processor.registerNewEntity(any(), any())).thenReturn(buildEntityErrorMessage()); when(processor.transformEntity(any(), any())).thenThrow(new IllegalArgumentException()); (*) startChannel.addInterceptor(new WireTap(errorChannel)); startChannel.send(buildErrorStartMessage()); verify(errorHandler,times(1)).processException(messageArgumentCaptor.capture());
我认为测试逻辑是正确的,请问该如何正确捕获错误?
解决方案
绑定错误通道到业务组件
仅给流程通道加WireTap无法实现异常路由,WireTap只是监听所有通道消息(包括正常消息)。需要在业务处理组件(比如服务激活器)上显式指定自定义错误通道,确保异常被Spring Integration的错误机制捕获并转发:@ServiceActivator(inputChannel = START_PROCESSING_CHANNEL, errorChannel = CUSTOM_ERROR_CHANNEL) public void processMessage(Message<?> message) { // 调用processor的业务逻辑 }用
MessageCaptor精准捕获错误消息
替换WireTap,使用Spring Integration测试提供的MessageCaptor专门监听错误通道的消息,避免捕获到原始发送的消息:@Autowired @Qualifier(CUSTOM_ERROR_CHANNEL) private MessageChannel errorChannel; private MessageCaptor errorMessageCaptor; @BeforeEach void setUp() { errorMessageCaptor = MessageCaptor.forChannel(errorChannel); }调整测试验证逻辑
抛出异常后,直接验证错误通道的消息内容,确保异常被正确封装并路由:// 模拟处理器抛出异常 when(processor.transformEntity(any(), any())).thenThrow(new IllegalArgumentException("测试异常")); // 发送消息到流程通道 startChannel.send(buildErrorStartMessage()); // 验证错误通道收到消息 Message<?> errorMsg = errorMessageCaptor.getNextMessage(); assertNotNull(errorMsg); // 检查异常封装是否正确 MessagingException msgException = (MessagingException) errorMsg.getPayload(); assertTrue(msgException.getCause() instanceof IllegalArgumentException);确保
errorHandler是错误通道的消费者
如果要验证errorHandler.processException被调用,必须把errorHandler绑定为自定义错误通道的处理器:@ServiceActivator(inputChannel = CUSTOM_ERROR_CHANNEL) public void handleError(Message<MessagingException> errorMessage) { errorHandler.processException(errorMessage.getPayload()); }这样错误通道收到消息时才会触发
errorHandler的方法,此时verify逻辑才能生效。
内容的提问来源于stack exchange,提问作者ovod
相关产品推荐
相关产品推荐

