Spring integration 分裂后平行富集

Spring integration 分裂后平行富集,spring-integration,Spring Integration,这是的延续,我们有一个外部API,允许从购物车结账。总而言之,我们有一个流程,在这个流程中,我们创建一个空购物,添加行项目,最后结帐。上面的所有操作都是通过对外部服务的HTTP调用来实现的。我们希望同时添加行项目(作为添加行项目调用的一部分)。我们当前的配置如下所示: @Bean public IntegrationFlow fullCheckoutFlow() { return f -> f.channel("inputChannel") .transf

这是的延续,我们有一个外部API,允许从购物车结账。总而言之,我们有一个流程,在这个流程中,我们创建一个空购物,添加行项目,最后结帐。上面的所有操作都是通过对外部服务的HTTP调用来实现的。我们希望同时添加行项目(作为添加行项目调用的一部分)。我们当前的配置如下所示:

@Bean
public IntegrationFlow fullCheckoutFlow() {
    return f -> f.channel("inputChannel")
            .transform(fromJson(ShoppingCart.class))
            .enrich(e -> e.requestChannel(SHOPPING_CART_CHANNEL))
            .split(ShoppingCart.class, ShoppingCart::getLineItems)
            .enrich(e -> e.requestChannel(ADD_LINE_ITEM_CHANNEL))
            .aggregate(aggregator -> aggregator
                    .outputProcessor(g -> g.getMessages()
                            .stream()
                            .map(m -> (LineItem) m.getPayload())
                            .map(LineItem::getName)
                            .collect(joining(", "))))
            .enrich(e -> e.requestChannel(CHECKOUT_CHANNEL))
            .<String>handle((p, h) -> Message.called("We have " + p + " line items!!"));
}

    @Bean
    public IntegrationFlow addLineItem(Executor executor) {
        return f -> f.channel(MessageChannels.executor(ADD_LINE_ITEM_CHANNEL, executor).get())
                .handle(outboundGateway("http://localhost:8080/api/add-line-item", restTemplate())
                        .httpMethod(POST)
                        .expectedResponseType(String.class));
    }

    @Bean
    public Executor executor(Tracer tracer, TraceKeys traceKeys, SpanNamer spanNamer) {
        return new TraceableExecutorService(newFixedThreadPool(10), tracer, traceKeys, spanNamer);
    }
@Bean
公共集成流FullCheckOutput(){
返回f->f.channel(“输入通道”)
.transform(fromJson(ShoppingCart.class))
.enrich(e->e.requestChannel(购物车通道))
.split(ShoppingCart.class,ShoppingCart::getLineItems)
.enrich(e->e.requestChannel(添加行项目通道))
.聚合(聚合器->聚合器
.outputProcessor(g->g.getMessages()
.stream()
.map(m->(LineItem)m.getPayload())
.map(LineItem::getName)
.collect(加入(“,”))
.enrich(e->e.requestChannel(签出通道))
.handle((p,h)->Message.called(“我们有“+p+”行项目!!”));
}
@豆子
公共集成流addLineItem(执行者执行者){
返回f->f.channel(MessageChannels.executor(ADD\u LINE\u ITEM\u channel,executor.get())
.handle(outboundGateway(“http://localhost:8080/api/add-行项目”,restTemplate())
.httpMethod(POST)
.expectedResponseType(String.class));
}
@豆子
公共遗嘱执行人遗嘱执行人(追踪器追踪器、追踪器追踪器、斯潘纳默斯潘纳默){
返回新的TraceableExecutorService(新的FixedThreadPool(10)、tracer、traceKeys、spanNamer);
}

为了并行添加行项目,我们使用一个executor通道。但是,当在zipkin中看到它们时,它们似乎仍在按顺序处理:

我们做错了什么?整个项目的来源是供参考的


谢谢

首先,Spring集成的主要功能是
MessageChannel
,但我仍然不清楚为什么人们在端点定义之间缺少
.channel()
操作符

我的意思是,对于你的情况,它必须是这样的:

.split(ShoppingCart.class, ShoppingCart::getLineItems)
.channel(c -> c.executor(executor()))
.enrich(e -> e.requestChannel(ADD_LINE_ITEM_CHANNEL))
现在谈谈你的特殊问题

看,
ContentEnricher
.enrich()
)是请求-应答组件:

因此,它将请求发送到其
requestChannel
,并等待回复。它独立于
requestChannel
类型来完成

I raw Java我们可以用以下代码片段演示这种行为:

for (Object item: items) {
    Data data = sendAndReceive(item);
}
您应该看到,
ADD\u LINE\u ITEM\u CHANNEL
作为一个
executor CHANNEL
没有太大价值,因为我们仍然被阻塞在回复的循环中

.split()
执行完全类似的循环,但由于默认情况下是使用
DirectChannel
,因此在同一线程中进行迭代。因此,下一个项目等待上一个项目的答复


这就是为什么在
.split()

之后,您一定要将并行作为
.rich()
的输入。所以,实际上我们正在做拆分器->执行器通道->充实。执行器通道是支持并行化的通道。我的理解正确吗?正确。enricher的requestChannel作为执行者之一是没有意义的,因为我们无论如何都会被阻止等待回复。