2017-08-18 2 views
1

私は次のように完全にページングされたリソースを消費しようとしていますが、私のaproachはStackOverflowExceptionを発生させています。 これは何か手掛かりですか?または別の方法ですか?ページングされたhttpリソースにアクセスする統合フロー

例:https://gist.github.com/daniel-frank/a88fa4553ed34c348528f51d33c3733b

+1

私には疑わしいものはありません。たぶんあなたは、StackOverflowExceptionのポイントを決定するために、この問題に関するスタックトレースを共有できますか? –

+0

Gistは完全なログファイルで更新されました。 –

答えて

1

OK。私は今参照してください。私は、問題を示すために、あなたの再帰的なコードを単純化してみましょう:

private IntegrationFlow getPageFlow() { 
     return f -> f 
       .publishSubscribeChannel(ps -> ps 
         .subscribe(this.nextPageFlow()) 
       ); 
    } 


private IntegrationFlow nextPageFlow() { 
     return f -> f 
       .publishSubscribeChannel(ps -> ps 
         .subscribe(this.getPageFlow()) 
       ); 
} 

だから、技術的に我々はメモリ内にこのような構造を持っていますので、上の

getPageFlow 
    nextPageFlow 
     getPageFlow 
      nextPageFlow 
       getPageFlow 

とを。

また、.subscribe(this.nextPageFlow())の新しいインスタンスはIntegrationFlowという新しいインスタンスを作成しますが、論理的には1つしかありません。

IntegrationFlowAdapterインプリメントで豆を宣言することはできませんが、とにかくStackOverflowExceptionではできません。

私があなたのアプローチで問題として見るものは、MessageChannel抽象化の欠如です。

どこでもpublishSubscribeChannelを使用していますが、フロー内の明示的なチャネル定義によって論理を区別することができます。

再帰を壊し、私はこのように作ると思い、可能な限りあなたの解決に近づくように、コードを保つために:、あなたはまだ再帰を持っているが、それは実行時にすでにでしょう。もちろん、

private IntegrationFlow getPageFlow() { 
     return f -> f 
       .channel("pageServiceChannel") 
       .handle(Http 
          .outboundGateway("https://jobs.github.com/positions.json?description={description}&page={page}") 
... 

    private IntegrationFlow nextPageFlow() { 
     return f -> f 
       .filter("!payload.isEmpty()") 
       .enrichHeaders(e -> e.headerExpression("page", "headers.getOrDefault('page', 0) + 1", true)) 
       .channel("pageServiceChannel"); 
    } 

を論理的。

+0

私は理解しています。チャンネルは、Spring Integrationの第一級市民です。でも、私は通常、フローをフローに接続するより「タイプセーフな」アプローチを好みます(たとえば、ルータのchannelMappingではなくsubFlowMapping)。ありがとうございました! –

+1

チャンネルを返すメソッドで "型の安全"を維持できます。しかし、私はあなたが何を意味するかを見ます。残念ながら、メソッドからメソッドを呼び出すだけで宣言の再帰を止めることはできません。 –

関連する問題