java Spring Integration:具有默认输出通道的基于内容的路由器?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/6845985/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-30 17:34:07  来源:igfitidea点击:

Spring Integration: Content based router with default output channel?

javaspringroutingspring-integration

提问by otto.poellath

I'd like use Spring Integration to implement a content based router that uses a default output channel if the expression value doesn't match any of the mappings. Here's my bean definition:

如果表达式值与任何映射都不匹配,我想使用 Spring Integration 来实现基于内容的路由器,该路由器使用默认输出通道。这是我的 bean 定义:

<int:router input-channel="channel_in" default-output-channel="channel_default" expression="payload.name">
    <int:mapping value="foo" channel="channel_one" />
    <int:mapping value="bar" channel="channel_two" />

However, it seems the default output channel is never used. If the expression evaluates to e.g. 'baz', the router seems to be looking for a channel named 'baz', instead of routing to the 'channel_default' channel:

但是,似乎从未使用过默认输出通道。如果表达式的计算结果为“baz”,则路由器似乎正在寻找名为“baz”的通道,而不是路由到“channel_default”通道:

org.springframework.integration.MessagingException: failed to resolve channel name 'baz'
  Caused by: org.springframework.integration.support.channel.ChannelResolutionException: 
    failed to look up MessageChannel bean with name 'baz'
  Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: 
    No bean named 'baz' is defined

Is what I want at all possible using the XML namespace, or do I need to code up my own implementation?

使用 XML 命名空间完全可以实现我想要的,还是需要编写自己的实现?

回答by otto.poellath

Turns out that all I had to to to make this work was to set the router's ignore-channel-name-resolution-failures attribute to false:

事实证明,要完成这项工作,我所要做的就是将路由器的 ignore-channel-name-resolution-failures 属性设置为 false:

<int:router input-channel="channel_in" default-output-channel="channel_default" 
  expression="payload.name" ignore-channel-name-resolution-failures="true">
    <int:mapping value="foo" channel="channel_one" />
    <int:mapping value="bar" channel="channel_two" />
</int:router>

I thought I had tried that before, but I seems I didn't.

我以为我以前试过,但我似乎没有。

回答by m190

As mentioned in reference docs:

参考文档中所述

As of Spring Integration 2.1, router parameters have been more standardized across all router implementations. Consequently, a few minor changes may break older Spring Integration based applications.

Since Spring Integration 2.1, the ignore-channel-name-resolution-failuresattribute is removed in favor of consolidating its behavior with the resolution-requiredattribute. Also, the resolution-required attribute now defaults to true.

Prior to these changes, the resolution-requiredattribute defaulted to false, causing messages to be silently dropped when no channel was resolved and no default-output-channelwas set. The new behavior requires at least one resolved channel and, by default, throws a MessageDeliveryExceptionif no channel was determined (or an attempt to send was not successful).

If you do desire to drop messages silently, you can set default-output-channel="nullChannel".

从 Spring Integration 2.1 开始,路由器参数在所有路由器实现中都更加标准化。因此,一些小的更改可能会破坏旧的基于 Spring Integration 的应用程序。

从 Spring Integration 2.1 开始,该 ignore-channel-name-resolution-failures属性已被删除,以支持将其行为与该resolution-required属性合并。此外,分辨率要求的属性现在默认为true

在这些更改之前,该resolution-required属性默认为 false,这会导致在未解析任何通道且未default-output-channel设置任何通道时静默丢弃消息。新行为至少需要一个已解析的通道,并且默认情况下,MessageDeliveryException如果未确定通道(或尝试发送未成功),则抛出 。

如果您确实希望静默删除消息,则可以设置 default-output-channel="nullChannel".

And if you are using Java DSL, the configuration may looks like this:

如果您使用的是 Java DSL,则配置可能如下所示:

IntegrationFlows.from("process")
        .<JobExecution, String>route(m -> m.getExitStatus().getExitCode(),
                m -> m.channelMapping(ExitStatus.COMPLETED.getExitCode(), "succeed")
                        .defaultOutputChannel("failed")
                        .resolutionRequired(false))
        .get();

回答by Ramneek Handa

if you are using for Spring boot 2.1.2.RELEASE

如果您使用的是 Spring Boot 2.1.2.RELEASE

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-integration</artifactId>
</dependency>

then resolution-required="false"is required instead of ignore-channel-name-resolution-failures.

然后需要 resolution-required="false"而不是 ignore-channel-name-resolution-failures。

<int:router input-channel="channel_in" default-output-channel="channel_default" 
  expression="payload.name" resolution-required="false">
    <int:mapping value="foo" channel="channel_one" />
    <int:mapping value="bar" channel="channel_two" />
</int:router>