AgentSkillsCN

test-design

通用测试设计与策略指南(不依赖于特定测试工具)。涵盖测试金字塔、测试层级的选择标准、测试优先级的确定、测试双模的选择(Stub/Mock/Fake/Spy)、测试设计模式(AAA/GWT)、命名规范、反模式识别,以及针对新功能/缺陷修复/遗留代码的不同测试策略和测试覆盖率考量等核心内容。适用于测试方针的制定、测试层级的选定以及测试设计等场景。

SKILL.md
--- frontmatter
name: test-design
description: テスト設計・戦略の汎用ガイド(テストツール非依存)。テストピラミッド、テストレベルの選択基準、何をテストすべきかの優先順位、テストダブルの選択(Stub/Mock/Fake/Spy)、テスト設計パターン(AAA/GWT)、命名規則、アンチパターン、新機能/バグ修正/レガシーコードごとのテスト戦略、テストカバレッジの考え方をカバー。テスト方針決定、テストレベル選択、テスト設計時に使用。

テスト設計ガイド

テストの設計・戦略に関する汎用ガイド。特定のテストフレームワークには依存しない。

テストピラミッド

code
        /\
       /  \      E2E(少)
      /────\     ユーザーフロー全体
     /      \
    /────────\   統合(中)
   /          \  コンポーネント間連携
  /────────────\ ユニット(多)
 /              \ 関数・クラス単体

原則: 下層ほど多く・高速・安定、上層ほど少なく・遅い・不安定

テストレベルの選択

レベル対象特徴
ユニット純粋関数、ビジネスロジック、ユーティリティ、状態変換高速、独立、デバッグ容易
統合API エンドポイント、DB 操作、外部サービス連携、コンポーネント間連携実際の連携検証、セットアップ必要
E2Eクリティカルなユーザーフロー、決済・認証最も現実的、遅い、不安定になりやすい

選択判断フロー

code
単体で検証可能な純粋ロジック?
├→ Yes → ユニットテスト
└→ No  → 複数コンポーネントの連携が関わる?
          ├→ Yes → 統合テスト
          └→ No  → ユーザーの操作フロー全体を検証?
                    ├→ Yes → E2E テスト
                    └→ No  → ユニットテスト

何をテストすべきか

優先度: 高

  1. ビジネスクリティカルなロジック - 決済計算、権限チェック、データ変換
  2. エッジケース - 境界値、null/undefined、空配列・空文字
  3. 過去にバグがあった箇所 - 回帰防止

優先度: 中

  1. 複雑な条件分岐
  2. 外部依存のある処理
  3. 状態管理ロジック

優先度: 低(または不要)

  • 単純な getter/setter
  • フレームワークの機能そのもの
  • 外部ライブラリの動作そのもの

テストダブルの選択

種類目的使用場面
Stub固定値を返す外部 API の戻り値を固定、特定の状態を再現
Mock呼び出しを検証メソッド呼び出しの確認、引数の検証
Fake簡易実装を提供InMemory Repository、状態を持つ代替
Spy実装を維持しつつ記録実際の処理 + 呼び出し回数の確認

選択フロー

code
呼び出しを検証したい?
├→ Yes → 実装も動かしたい?
│         ├→ Yes → Spy
│         └→ No  → Mock
└→ No  → 状態を持つ必要がある?
          ├→ Yes → Fake
          └→ No  → Stub

ベストプラクティス

code
1. 境界でのみダブルを使う(外部システム、時間、乱数)
2. Fake を優先(InMemory 実装は再利用可能、実際の動作に近い)
3. Mock は最小限に(副作用の検証時のみ)
4. 「何が呼ばれたか」より「何が起きたか」に注目

詳細: references/test-doubles.md

テスト設計パターン

AAA パターン

code
Arrange: 準備(データ、依存関係のセットアップ)
Act:     実行(テスト対象の呼び出し)
Assert:  検証(期待結果との比較)

Given-When-Then

code
Given: 前提条件(システムがこの状態のとき)
When:  アクション(この操作を行うと)
Then:  期待結果(こうなるべき)

使い分け

code
AAA:            ユニットテスト向き(技術者視点)
Given-When-Then: 統合/E2E テスト向き(ビジネス視点)

テスト命名規則

code
{対象}_{条件}_{期待結果}

例:
  calculateTotal_withEmptyCart_returnsZero
  login_withInvalidPassword_throwsError
  fetchUser_whenNotFound_returnsNull

原則

code
- テスト名だけで何をテストしているか分かる
- 条件と期待結果を含める
- 実装詳細ではなく振る舞いを記述

テストデータの設計

code
原則:
  - テストごとに独立したデータを用意
  - 共有のテストデータに依存しない
  - ファクトリ/ビルダーパターンでデータ生成を共通化
  - 意味のあるデータを使う(マジックナンバーを避ける)

データ生成の階層:
  1. テスト内で直接定義(最もシンプル)
  2. ヘルパー関数/ファクトリ(再利用する場合)
  3. Fixture(セットアップが複雑な場合)

アンチパターン

パターン問題解決
テストの相互依存実行順序で結果が変わる各テストで状態をリセット
過度なモック実装詳細に依存しすぎ境界でのみモック
巨大なテスト1テストで多くを検証1テスト1責務
マジックナンバーデータの意図が不明意味のある変数名
テストの重複同じことを複数箇所で検証責務を明確に分離
脆いアサーション変更に弱い完全一致本質的な部分のみ検証
条件分岐のあるテストテスト内に if 文ケースごとにテスト分離
非決定的テスト時刻・乱数で結果が変わる依存を注入可能に
コメントアウトされたテスト無効化されたテスト放置削除するか修正
アサーションなし何も検証していない必ず expect を含める

詳細: references/anti-patterns.md

実装ワークフロー

新機能のテスト

code
1. 要件からテストケースを洗い出す
2. 優先度でソート(ビジネスクリティカル → エッジケース)
3. ユニットテストから書く
4. 必要に応じて統合テスト追加
5. クリティカルパスは E2E テスト

バグ修正のテスト(TDD アプローチ)

code
1. バグを再現するテストを先に書く(Red)
2. 修正を実装(Green)
3. リファクタリング
4. 回帰テストとして維持

レガシーコードのテスト

code
1. 変更箇所を特定
2. その箇所の現状動作をテスト化(Characterization Test)
3. テストが通ることを確認
4. 変更を加える
5. テストが通ることを再確認

テストカバレッジの考え方

code
原則:
  - カバレッジは「テストの質」の指標ではない
  - カバレッジが低い箇所を発見するための参考値
  - 100% を目標にしない(投資対効果が低い)

推奨:
  - ビジネスロジック: 80%+ を目安
  - ユーティリティ: 90%+ を目安
  - UI コンポーネント: 重要な操作フローをカバー
  - 設定・ボイラープレート: カバレッジ対象外でも可

注意:
  - カバレッジ閾値を CI に組み込む場合は段階的に引き上げる
  - ブランチカバレッジ > ラインカバレッジ(条件分岐の網羅度)

レビューチェックリスト

  • テストレベルが適切に選択されている
  • ビジネスクリティカルなロジックがテストされている
  • エッジケース(境界値、null、空)がテストされている
  • テストが相互に独立している
  • テストダブルが境界でのみ使われている
  • テスト名から何をテストしているか分かる
  • 1テスト1アサーション(または1責務)
  • マジックナンバーがない

リファレンス