7

私の仮定

私の理解では、Spring Batch の「チャンク指向の処理」は、1 つのトランザクションで複数のアイテムを効率的に処理するのに役立ちます。これには、外部システムからのインターフェースの効率的な使用が含まれます。外部通信にはオーバーヘッドが含まれるため、制限され、チャンク指向でもある必要があります。そのため、 のコミット レベルがありItemWriterます。だから私が得られないのは、なぜItemReaderまだ項目ごとに読まなければならないのですか? チャンクも読めないのはなぜですか?

問題の説明

私のステップでは、リーダーは Web サービスを呼び出す必要があります。そして、ライターはこの情報を別の Web サービスに送信します。そのため、必要なだけ呼び出しを行いたくないのです。

のインターフェースItemWriterはチャンク指向です - ご存じのように:

public abstract void write(List<? extends T> paramList) throws Exception;

しかし、ItemReaderそうではありません:

public abstract T read() throws Exception;

回避策として、アイテムのリストを読み取り、それらを保存し、そのメソッドが呼び出されるChunkBufferingItemReaderたびにアイテムを 1 つずつ返すを実装しました。read()

しかし、現在、例外処理とジョブの再開に関しては、このアプローチは厄介になっています。フレームワークが私のためにしてくれるはずの、ここで仕事をしているような気がします。

質問

それで、私は何かを逃していますか?見落としていた Spring Batch の既存の機能はありますか?

別の投稿では、 の戻り値の型を に変更することが提案されItemReaderましたList。しかし、その後、ItemProcessor単一の入力から複数の出力を発行する必要があります。これは正しいアプローチですか?

私はどんなベストプラクティスにも優雅です。前もって感謝します :-)

4

2 に答える 2

4

これは、read() インターフェイス メソッドの実装のドラフトです。

public T read() throws Exception {
    while (this.items.isEmpty()) {
        final List<T> newItems = readChunk();
        if (newItems == null) {
            return null;
        }
        this.items.addAll(newItems);
    }
    return this.items.pop();
}

itemsこれは、チャンクで読み取られ、フレームワークによってまだ要求されていないアイテムのバッファーであることに注意してください。

于 2014-02-20T19:22:04.723 に答える
0

Spring Batch は「チャンク指向」処理スタイルを使用します。(チャンクの読み取りや書き込みだけでなく、読み取り、処理、書き込みを含む完全なプロセス)

チャンク指向処理とは、

  1. ItemReader (Single Item) を使用してアイテムを読み取る
  2. それをItemProcessorで処理し、結果を集計します(結果リストは順次更新されます)。
  3. コミット間隔に達すると、集計結果全体 (結果リスト) が ItemWriter を使用して書き出され、トランザクションがコミットされます。

SpringBatch doc のコード表現は次のとおりです

List items = new Arraylist();
for(int i = 0; i < commitInterval; i++){
    Object item = itemReader.read()
    Object processedItem = itemProcessor.process(item);
    items.add(processedItem);
}
itemWriter.write(items);

あなたが言ったように、リーダーが複数のアイテムを返す必要がある場合は、それをListにします。また、プロセッサもListを返す場合。最後に、Writer はList の Listを取得します。

新しいケースのコード表現は次のとおりです

List<List<Object>> resultList = new Arraylist<List<Object>>();
for(int i = 0; i < commitInterval; i++){
    List<Object> items = itemReader.read()
    List<Object> processedItems = itemProcessor.process(items);
    resultList.add(processedItems);
}
itemWriter.write(resultList);
于 2013-02-18T16:55:39.983 に答える