4

春の統合スプリッター ロジックでは、空を返す可能性があるArrayListため、ルーティングするデータが提供されない場合があります。ArrayListスプリッターから空が返された場合、このシナリオをどのように処理し、別のチャネルに再ルーティングする必要がありますか。

アップデート :

Artem が示すように、私はカスタム アドバイスを作成し、再ルーティングを正常に実行しましたが、まだ 2 つの問題があります。

私が持っている現在のクラスは次のとおりです

public class EmptyListRequestHandlerAdvice extends AbstractRequestHandlerAdvice {

    private final MessagingTemplate messagingTemplate = new MessagingTemplate();

    public EmptyListRequestHandlerAdvice(MessageChannel emptyListChannel) {
        this.messagingTemplate.setDefaultChannel(emptyListChannel);
    }

    @Override
    protected Object doInvoke(ExecutionCallback callback, Object target,
            Message<?> message) throws Exception {
        Object result = callback.execute();

        if (result==null) {
            this.messagingTemplate.convertAndSend(new ArrayList<InventoryHotel>());
        }

        return result;
    }

スプリッターが新しい空の配列リストを返すたびに、「callback.execute() の結果は null です。ただし、スプリッターから返された配列リストが空でない場合は常に、返される結果は org.springframework.integration.util.FunctionIterator 型であり、型ではありません。コレクション型 null または関数イテレータの代わりに両方のケースで返されるコレクションを取得できるかどうかについて何か考えはありますか? 少なくとも関数イテレータの取得を避け、配列リストを取得してください。

さらに、有効なチャネル名がコンストラクターに設定され、メッセージがそのチャネルを介してトランスフォーマー メソッドに送信されると、トランスフォーマー メソッドは正常に実行されますが、値が返されると、次のエラーが発生します。

org.springframework.messaging.MessagingException: org.springframework.messaging.core.DestinationResolutionException: no output-channel or replyChannel header available
    at org.springframework.integration.dispatcher.AbstractDispatcher.wrapExceptionIfNecessary(AbstractDispatcher.java:133)
    at org.springframework.integration.dispatcher.AbstractDispatcher.tryOptimizedDispatch(AbstractDispatcher.java:120)
    at org.springframework.integration.dispatcher.UnicastingDispatcher.doDispatch(UnicastingDispatcher.java:101)
    at org.springframework.integration.dispatcher.UnicastingDispatcher.dispatch(UnicastingDispatcher.java:97)
    at org.springframework.integration.channel.AbstractSubscribableChannel.doSend(AbstractSubscribableChannel.java:77)
    at org.springframework.integration.channel.AbstractMessageChannel.send(AbstractMessageChannel.java:255)

これが発生する理由と解決方法に関する提案。

よろしく、ミリンダ

4

1 に答える 1

2

まあ、あなたはそれを克服することができます<request-handler-advice-chain>for<splitter>ともちろんいくつかのカスタムAbstractRequestHandlerAdvice:

public class EmptyListRequestHandlerAdvice extends AbstractRequestHandlerAdvice {

    private final MessagingTemplate messagingTemplate = new MessagingTemplate();

    public EmptyListRequestHandlerAdvice(MessageChannel emptyListChannel) {
         this.messagingTemplate.setDefaultChannel(emptyListChannel);
    }

    @Override
    protected Object doInvoke(ExecutionCallback callback, Object target, Message<?> message) throws Exception {
          Collection<?> result = (Collection<?>) callback.execute();
          if (result.isEmpty) {
             this.messagingTemplate.convertAndSend(result);
          }
          return result;
     }

} 

アップデート

そのクラスを使用すると、次のように使用できます。

<splitter>
  <request-handler-advice-chain>
      <beans:bean class="com.my.proj.int.EmptyListRequestHandlerAdvice">
          <beans:constructor-arg ref="emptyListChannel"/>
      </beans:bean>
  </request-handler-advice-chain>
</splitter>

<channel id="emptyListChannel"/>

UPDATE2

nullまたは関数イテレータの代わりに、両方のケースで返されるコレクションを取得できるかどうかについてのアイデアはありますか?

いいえ、できません。これはスプリッターの内部ロジックであり、その結果、スプリット プロセス ゲインがhandleRequestMessage生成されます。スプリッターは常にいくつかのメッセージを生成し、反復ロジックは隠されているため、 を使用する理由は明確ではありません。IteratorstreamingCollection

最初の要件から、空のリストを別のチャネルに送信するソリューションを求めました。したがって、反復子ロジックが影響を与える理由がわかりません。

output-channel または replyChannel ヘッダーは利用できません

あなたは本当にこれを行う必要があります:

this.messagingTemplate.send(MessageBuilder.withPayload(new ArrayList<InventoryHotel>())
      .copyHeaders(message.getHeaders().build());

その requestMessage に基づいて新しいメッセージを作成すると、そのすべてのヘッダーがコピーされるため、replyChannelヘッダーも存在します。

于 2014-10-20T13:26:24.173 に答える