Apache Commons Chain

Apache Commons Chain

1. 前書き

Apache Commons Chainは、Chain of Responsibilitypatternを使用するライブラリです。通常、複数の受信者がリクエストを処理できる複雑な処理フローを整理するために使用されます。

この簡単な記事では、ATMからの引き出しを表す例を紹介します。

2. メーベン依存

まず、Mavenを使用してこのライブラリの最新バージョンをインポートします。


    commons-chain
    commons-chain
    1.2

このライブラリの最新バージョンを確認するには–go here

3. チェーンの例

ATMは番号を入力として受け取り、さまざまなアクションの実行を担当するハンドラーに渡します。 それらは、分配される銀行券の数を計算し、取引について銀行と顧客に通知を送信することを伴います。

4. チェーンコンテキスト

コンテキストはアプリケーションの現在の状態を表し、トランザクションに関する情報を保存します。

ATMの出金リクエストに必要な情報は次のとおりです。

  • 引き出される合計金額

  • 100分音符の数

  • 50分音符の数

  • 10分音符の数

  • 引き出し残額

この状態はクラスで定義されます:

public class AtmRequestContext extends ContextBase {
    int totalAmountToBeWithdrawn;
    int noOfHundredsDispensed;
    int noOfFiftiesDispensed;
    int noOfTensDispensed;
    int amountLeftToBeWithdrawn;

    // standard setters & getters
}

5. コマンド

Commandは、Contextを入力として受け取り、それを処理します。

上記の各ステップをCommand:として実装します

public class HundredDenominationDispenser implements Command {

    @Override
    public boolean execute(Context context) throws Exception {
        intamountLeftToBeWithdrawn = (int) context.get("amountLeftToBeWithdrawn);
        if (amountLeftToBeWithdrawn >= 100) {
            context.put("noOfHundredsDispensed", amountLeftToBeWithdrawn / 100);
            context.put("amountLeftToBeWithdrawn", amountLeftToBeWithdrawn % 100);
        }
        return false;
    }
}

FiftyDenominationDispenserTenDenominationDispenserCommandsは類似しています。

6. 鎖

Chainは、指定された順序で実行されるコマンドのコレクションです。 Chainは、上記のCommandsと、最後のAuditFilterで構成されます。

public class AtmWithdrawalChain extends ChainBase {

    public AtmWithdrawalChain() {
        super();
        addCommand(new HundredDenominationDispenser());
        addCommand(new FiftyDenominationDispenser());
        addCommand(new TenDenominationDispenser());
        addCommand(new AuditFilter());
    }
}

Chain内のCommandがtrueを返すと、Chainは強制的に終了します。

7. フィルタ

フィルタもCommandですが、Chain.の実行後に呼び出されるpostProcessメソッドを使用します

Filterは、顧客と銀行に通知を送信します。

public class AuditFilter implements Filter {

    @Override
    public boolean postprocess(Context context, Exception exception) {
        // send notification to bank and user
        return false;
    }

    @Override
    public boolean execute(Context context) throws Exception {
        return false;
    }
}

8. チェーンカタログ

これは、ChainsCommandsの論理名を持つコレクションです。

この場合、CatalogにはAtmWithdrawalChain.が含まれます

public class AtmCatalog extends CatalogBase {

    public AtmCatalog() {
        super();
        addCommand("atmWithdrawalChain", new AtmWithdrawalChain());
    }
}

9. チェーンの使用

上記のChainを使用して引き出しリクエストを処理する方法を見てみましょう。 最初にContextを作成し、次にChain.を渡します。ChainContext.を処理します。

AtmWithdrawalChain:を示すテストケースを作成します

public class AtmChainTest {

    @Test
    public void givenInputsToContext_whenAppliedChain_thenExpectedContext() throws Exception {
        Context context = new AtmRequestContext();
        context.put("totalAmountToBeWithdrawn", 460);
        context.put("amountLeftToBeWithdrawn", 460);

        Catalog catalog = new AtmCatalog();
        Command atmWithdrawalChain = catalog.getCommand("atmWithdrawalChain");

        atmWithdrawalChain.execute(context);

        assertEquals(460, (int) context.get("totalAmountToBeWithdrawn"));
        assertEquals(0, (int) context.get("amountLeftToBeWithdrawn"));
        assertEquals(4, (int) context.get("noOfHundredsDispensed"));
        assertEquals(1, (int) context.get("noOfFiftiesDispensed"));
        assertEquals(1, (int) context.get("noOfTensDispensed"));
    }
}

10. 結論

このチュートリアルでは、ApacheのApache Commonsチェーンライブラリを使用して実際のシナリオを検討しました。これについては、hereについて詳しく読むことができます。

そして、いつものように、この記事のコードはover on Githubで利用できます。