結合テストとは何か
結合テストとは、複数のモジュール(機能)間の相互作用をテストする手法です。具体的には以下のような特徴があります。
- 定義
- 複数のモジュールを組み合わせて行うテスト
- モジュール間のデータの受け渡しや連携の正確性を確認
- 単体テストとの違い
単体テストは1つの部品だけをテストします。以下の例では「価格計算」だけを確認しています。
一方、結合テストは複数の部品を組み合わせた際の動作をテストします。以下の例では「注文処理全体の流れ」をテストしています。
// 単体テスト:計算ロジックのみをテスト
@Test
public void testCalculation() {
PriceCalculator calculator = new PriceCalculator();
int price = calculator.calculate(100, 0.1); // 単一の機能
assertEquals(110, price); // 価格が正しいか確認
}
// 結合テスト:注文処理全体の流れをテスト
@Test
public void testOrderProcess() {
OrderService orderService = new OrderService(
priceCalculator, // 価格計算モジュール
inventoryService // 在庫管理モジュール
);
Order order = orderService.createOrder("ITEM-1", 2); // 複数モジュールの連携
assertNotNull(order); // 注文が作成されたか確認
assertEquals("ITEM-1", order.getItemId()); // 注文IDが正しいか確認
assertEquals(220, order.getTotalPrice()); // 合計金額が正しいか確認
}
なぜ結合テストが必要なのか
結合テストが必要となる理由は、以下の3つに集約されます。
- データの整合性確保
モジュール同士がデータを正しく受け渡せるかを確認します。
例として、「注文処理」と「在庫管理」のモジュールを考えます。- 問題例1:データの形式の違い
「注文処理モジュール」は商品IDを文字列("12345"
)で扱うが、「在庫管理モジュール」は数値(12345
)として扱っている場合、連携エラーが起こる。 - 問題例2:欠陥データの処理
注文処理で「購入個数=0」が渡された場合、在庫側で適切に処理されず、在庫が不正に減る可能性がある。 - 確認するポイント
モジュール間でデータ型やフォーマットが一致しているか?
境界値(例:購入個数が0や最大値)の場合も正しく動くか?
- 問題例1:データの形式の違い
- 依存関係の検証
モジュールが期待通りに連携できるかを確認します。
連携時にはタイミングや依存する外部要素の影響で問題が発生することがあります。- 問題例1:同期と非同期の問題
「ユーザー登録」モジュールが新規登録を完了する前に、「メール通知」モジュールが動き出し、登録されていないユーザーにメールを送る可能性。 - 問題例2:環境依存の問題
開発環境では正常に動くが、本番環境の違う設定(例:異なるデータベースやAPIのタイムアウト時間)でエラーが出る。 - 確認するポイント
モジュールが正しい順序で動くか?
本番環境と似た条件で動作が保証されるか?
- 問題例1:同期と非同期の問題
- システム全体の信頼性向上
システム全体の安全性やパフォーマンスを確認します。
一部のモジュールの問題がシステム全体に悪影響を与えないようにする必要があります。- 問題例1:エラーが適切に処理されない
「支払い処理モジュール」で失敗したときに、注文がそのまま完了したことになる(在庫が減る、請求が不正に行われる)。 - 問題例2:トランザクション管理の失敗
途中でエラーが発生した場合、システムが一部だけ変更を適用してしまい、不整合が発生する(例:お金は引き落とされるが商品が発送されない)。 - 問題例3:パフォーマンスの問題
一度に大量の注文が発生した際、システムが耐えられずに全体が停止する。 - 確認するポイント
エラー時にシステムが安全に戻るか(ロールバック)?
高負荷時にスムーズに処理が行えるか?
- 問題例1:エラーが適切に処理されない