# 帳票設計書 3-SummaryReporter

## 概要

本ドキュメントは、Jestテストフレームワークにおけるサマリーレポーター「SummaryReporter」の設計仕様を定義する。SummaryReporterは、テスト実行完了後に全体のサマリー情報を出力するレポーターであり、合計テスト数、成功・失敗数、実行時間、スナップショット状態などを集約して表示する。

### 本帳票の処理概要

SummaryReporterは、Jestのテスト実行が完了した後に呼び出され、全テストの実行結果を集約したサマリー情報を出力する。テストスイート数、テストケース数、スナップショットの状態、実行時間などの統計情報を一覧形式で表示し、テスト実行全体の成功・失敗状態を把握できるようにする。大量のテストが失敗した場合には、失敗したテストのサマリーを再度表示する機能も持つ。

**業務上の目的・背景**：テスト実行後、全体の結果を一目で把握することは、品質管理とデプロイ判断において重要である。SummaryReporterは、テストスイート数、合格・不合格テスト数、スナップショットの状態、実行時間などの統計情報を集約し、CI/CDパイプラインでの自動判定やデベロッパーによる品質確認を支援する。また、多数のテストが失敗した場合に失敗サマリーを再表示することで、重要な情報の見落としを防ぐ。

**帳票の利用シーン**：すべてのJestテスト実行終了時に自動的に出力される。CI/CDビルド結果の確認、日次テストレポートの確認、リリース前の品質チェックなどに利用される。

**主要な出力内容**：
1. シード値（showSeed設定時）
2. テストスイート数（合格/不合格/スキップ/合計）
3. テスト数（合格/不合格/スキップ/TODO/合計）
4. スナップショット数（追加/更新/失敗/廃止/合計）
5. 実行時間（進捗バー付き）
6. 失敗テストのサマリー（閾値超過時）
7. スナップショット更新コマンドの案内

**帳票の出力タイミング**：onRunCompleteイベント時、すべてのテスト実行が完了した後に一度だけ出力される。

**帳票の利用者**：ソフトウェア開発者、QAエンジニア、DevOpsエンジニア、プロジェクトマネージャー、CI/CDシステム

## 帳票種別

テスト結果サマリーレポート / 統計情報レポート

## 利用画面

| 画面No | 画面名 | URL/ルーティング | 出力操作 |
|--------|--------|-----------------|---------|
| CLI-01 | コマンドライン | N/A | `jest`コマンド実行完了時 |
| CI-01 | CI/CDログ | N/A | テスト実行完了時 |

## 出力形式

### 基本仕様

| 項目 | 内容 |
|-----|------|
| ファイル形式 | テキスト（コンソール出力） |
| 用紙サイズ | N/A（ターミナル幅に依存） |
| 向き | N/A |
| ファイル名 | N/A（標準エラー出力） |
| 出力方法 | process.stderr への出力 |
| 文字コード | UTF-8 |

### コンソール出力設定

| 項目 | 内容 |
|-----|------|
| 色出力 | chalk ライブラリによるANSIカラー対応 |
| 進捗バー | 推定時間と実行時間の比率でUnicode文字表示 |
| 出力先 | process.stderr（安全な文字単位出力） |

## 帳票レイアウト

### レイアウト概要

SummaryReporterの出力は、統計情報とスナップショット情報、実行時間情報で構成される。

```
┌─────────────────────────────────────┐
│   失敗テストサマリー（閾値超過時）    │
├─────────────────────────────────────┤
│   スナップショットサマリー           │
├─────────────────────────────────────┤
│   Seed:        12345                │
│   Test Suites: 1 failed, 9 passed   │
│   Tests:       2 failed, 98 passed  │
│   Snapshots:   5 passed, 5 total    │
│   Time:        5.123s               │
│   ████████████░░░░░░░░░░░░░░░░      │
├─────────────────────────────────────┤
│   Ran all test suites.              │
└─────────────────────────────────────┘
```

### 失敗テストサマリー部（条件付き）

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | サマリータイトル | "Summary of all failing tests" | 固定値 | 太字 |
| 2 | 失敗テスト結果 | 各失敗テストのヘッダーとメッセージ | AggregatedResult.testResults | FAIL + パス + メッセージ |

### スナップショットサマリー部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | タイトル | "Snapshot Summary" | 固定値 | 太字 |
| 2 | 追加数 | 新規追加されたスナップショット | SnapshotSummary.added | 緑色 + ファイル数 |
| 3 | 失敗数 | 一致しなかったスナップショット | SnapshotSummary.unmatched | 赤色 + 更新コマンド |
| 4 | 更新数 | 更新されたスナップショット | SnapshotSummary.updated | 緑色 + ファイル数 |
| 5 | 削除ファイル数 | 削除されたスナップショットファイル | SnapshotSummary.filesRemoved | 緑/黄色 |
| 6 | 廃止数 | 未使用のスナップショット | SnapshotSummary.unchecked | 黄色 + キー一覧 |

### 統計情報部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | Seed | テスト実行のシード値 | globalConfig.seed | 数値 |
| 2 | Test Suites | テストスイート統計 | AggregatedResult | 色分け統計 |
| 3 | Tests | テストケース統計 | AggregatedResult | 色分け統計 |
| 4 | Snapshots | スナップショット統計 | AggregatedResult.snapshot | 色分け統計 |
| 5 | Time | 実行時間 | Date.now() - startTime | 秒表示 + 進捗バー |

### テスト情報部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | 実行情報 | "Ran all test suites" | 固定値 | 薄い色 |
| 2 | パス情報 | テストパスパターン | testPathPatterns | 薄い色 |
| 3 | 名前情報 | テスト名パターン | testNamePattern | 薄い色 |
| 4 | プロジェクト情報 | プロジェクト数 | testContexts.size | 薄い色 |

## 出力条件

### 抽出条件

| 条件名 | 説明 | 必須 |
|-------|------|-----|
| テストスイート存在 | numTotalTestSuites > 0 | Yes |
| 失敗サマリー表示 | failedTests + runtimeErrors > 0 かつ numTotalTestSuites > summaryThreshold | No |
| スナップショットサマリー表示 | added, filesRemoved, unchecked, unmatched, updated のいずれかが存在 | No |
| シード表示 | showSeed === true | No |

### ソート順

N/A（固定レイアウト）

### 改ページ条件

N/A（コンソール出力のためスクロール表示）

## データベース参照仕様

### 参照テーブル一覧

N/A（メモリ上の集約結果を使用）

### データ構造参照

#### AggregatedResult

| 参照項目 | 帳票項目との対応 | 用途 |
|---------|----------------|------|
| startTime | 実行時間計算 | 開始時刻 |
| numTotalTestSuites | Test Suites | 合計スイート数 |
| numPassedTestSuites | Test Suites | 合格スイート数 |
| numFailedTestSuites | Test Suites | 不合格スイート数 |
| numPendingTestSuites | Test Suites | スキップスイート数 |
| numTotalTests | Tests | 合計テスト数 |
| numPassedTests | Tests | 合格テスト数 |
| numFailedTests | Tests | 不合格テスト数 |
| numPendingTests | Tests | スキップテスト数 |
| numTodoTests | Tests | TODOテスト数 |
| snapshot | Snapshots | スナップショット統計 |
| testResults | 失敗サマリー | 各テスト結果 |
| wasInterrupted | 中断メッセージ | 中断フラグ |

## 計算仕様

### 計算項目一覧

| 項目名 | 計算式 | 端数処理 | 備考 |
|-------|-------|---------|------|
| 実行時間(秒) | (Date.now() - startTime) / 1000 | 切り捨て（roundTime時） | roundTimeオプション対応 |
| 進捗バー長 | Math.floor((runTime / estimatedTime) * availableWidth) | 切り捨て | 最大PROGRESS_BAR_WIDTH(40) |
| suitesRun | suitesFailed + suitesPassed | なし | 完了スイート数 |

## 処理フロー

### 出力フロー

```mermaid
flowchart TD
    A[onRunComplete] --> B{numTotalTestSuites > 0?}
    B -->|No| Z[終了]
    B -->|Yes| C[改行出力調整]
    C --> D[_printSummary]
    D --> E{失敗テストあり かつ 閾値超過?}
    E -->|Yes| F[失敗サマリー出力]
    E -->|No| G[スキップ]
    F --> H[_printSnapshotSummary]
    G --> H
    H --> I{スナップショット変更あり?}
    I -->|Yes| J[スナップショットサマリー出力]
    I -->|No| K[スキップ]
    J --> L[getSummary]
    K --> L
    L --> M[統計情報出力]
    M --> N{wasInterrupted?}
    N -->|Yes| O[中断メッセージ出力]
    N -->|No| P[_getTestSummary]
    O --> Q[終了]
    P --> Q
```

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 表示メッセージ | 対処方法 |
|----------|---------|--------------|---------|
| テスト中断 | wasInterrupted === true | "Test run was interrupted." | 赤太字で表示 |
| summaryThresholdエラー | オプションが数値でない | "The option summaryThreshold should be a number" | TypeError をスロー |

## パフォーマンス要件

| 項目 | 内容 |
|-----|------|
| 想定データ件数 | 数万テストケースの集計まで対応 |
| 目標出力時間 | 集計完了後即時（ミリ秒オーダー） |
| 同時出力数上限 | 1（シングルスレッド出力） |

## セキュリティ考慮事項

- サマリー情報には直接的な機密情報は含まれないが、テスト数やカバレッジ率からプロジェクト規模が推測可能
- 失敗サマリーにはエラーメッセージが含まれるため、機密情報の露出に注意
- CI/CDログの公開範囲を適切に設定すること

## 備考

- summaryThresholdオプション（デフォルト: 20）で、失敗サマリーを表示する閾値を設定可能
- スナップショット更新コマンドは、実行環境（npm/yarn）とスクリプト名を自動検出して表示
- watchモードでは `press \`u\`` と表示される
- Node.jsの終了タイミング問題を回避するため、文字単位での出力を行う（_writeメソッド）

---

## コードリーディングガイド

本帳票を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

まず、サマリーレポートで使用されるデータ構造を理解することが重要。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | types.ts | `packages/jest-reporters/src/types.ts` | SummaryOptions の定義（66-73行目）を確認 |
| 1-2 | @jest/test-result | `node_modules/@jest/test-result` | AggregatedResult, SnapshotSummary 型を確認 |

**読解のコツ**: SummaryReporterは集約結果を扱うため、AggregatedResultの構造を理解することが重要。

#### Step 2: エントリーポイントを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | SummaryReporter.ts | `packages/jest-reporters/src/SummaryReporter.ts` | クラス定義とコンストラクタ（55-71行目） |

**主要処理フロー**:
1. **62-71行目**: コンストラクタ - globalConfig設定、summaryThresholdオプション処理
2. **73-80行目**: _validateOptions - オプションのバリデーション

#### Step 3: メイン出力処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | SummaryReporter.ts | `packages/jest-reporters/src/SummaryReporter.ts` | onRunComplete（101-140行目） |

**主要処理フロー**:
- **101-140行目**: `onRunComplete` - メインの出力ロジック
- **106-117行目**: 最後のテストが成功した場合の改行調整
- **119行目**: `_printSummary` - 失敗テストサマリーの出力
- **120-123行目**: `_printSnapshotSummary` - スナップショットサマリーの出力
- **125-129行目**: `getSummary` - 統計情報の生成
- **131-137行目**: 中断時または通常時のメッセージ出力

#### Step 4: 失敗サマリー出力を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | SummaryReporter.ts | `packages/jest-reporters/src/SummaryReporter.ts` | _printSummary（185-208行目） |

**主要処理フロー**:
- **191-196行目**: summaryThreshold を超えた場合のみ失敗サマリーを出力
- **197行目**: "Summary of all failing tests" タイトル出力
- **198-205行目**: 各失敗テストのヘッダーとメッセージを出力
- **201-204行目**: `_write`メソッドで安全に文字単位出力

#### Step 5: スナップショットサマリー出力を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 5-1 | SummaryReporter.ts | `packages/jest-reporters/src/SummaryReporter.ts` | _printSnapshotSummary（142-183行目） |
| 5-2 | getSnapshotSummary.ts | `packages/jest-reporters/src/getSnapshotSummary.ts` | スナップショットサマリー生成 |

**主要処理フロー**:
- **146-152行目**: スナップショット変更がある場合のみ出力
- **153-172行目**: 更新コマンドの決定（watch/npm/yarn）
- **174-179行目**: `getSnapshotSummary`で詳細サマリーを生成

#### Step 6: 統計情報生成を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 6-1 | getSummary.ts | `packages/jest-reporters/src/getSummary.ts` | 統計情報の生成 |

**主要処理フロー**:
- **82-198行目**: `getSummary` - メインの統計生成関数
- **119-125行目**: シード値の出力（showSeed時）
- **127-135行目**: テストスイート統計の生成
- **147-161行目**: テスト統計の生成
- **163-193行目**: スナップショット統計の生成
- **54-80行目**: `renderTime` - 進捗バー付き時間表示

### プログラム呼び出し階層図

```
SummaryReporter
    │
    ├─ BaseReporter (継承)
    │
    ├─ onRunComplete
    │      │
    │      ├─ _printSummary
    │      │      ├─ getResultHeader
    │      │      └─ _write (文字単位出力)
    │      │
    │      ├─ _printSnapshotSummary
    │      │      └─ getSnapshotSummary
    │      │             └─ formatTestPath
    │      │
    │      ├─ getSummary
    │      │      ├─ getValuesCurrentTestCases
    │      │      ├─ renderTime
    │      │      └─ formatTime
    │      │
    │      └─ _getTestSummary
    │
    └─ _validateOptions
```

### データフロー図

```
[入力]                        [処理]                           [出力]

AggregatedResult ───────▶ onRunComplete
       │                       │
       │                       ├─▶ _printSummary ─────────────▶ 失敗サマリー
       │                       │         │
       │                       │         └─▶ getResultHeader
       │                       │
       │                       ├─▶ _printSnapshotSummary ────▶ スナップショットサマリー
       │                       │         │
       ▼                       │         └─▶ getSnapshotSummary
SnapshotSummary                │
       │                       ├─▶ getSummary ───────────────▶ 統計情報
       │                       │         │
       │                       │         ├─▶ Test Suites
       │                       │         ├─▶ Tests
       │                       │         ├─▶ Snapshots
       │                       │         └─▶ Time + 進捗バー
       │                       │
       └───────────────────────┴─▶ _getTestSummary ──────────▶ 実行情報
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| SummaryReporter.ts | `packages/jest-reporters/src/SummaryReporter.ts` | ソース | サマリーレポーター実装 |
| BaseReporter.ts | `packages/jest-reporters/src/BaseReporter.ts` | ソース | 基底クラス |
| getSummary.ts | `packages/jest-reporters/src/getSummary.ts` | ソース | 統計情報生成 |
| getSnapshotSummary.ts | `packages/jest-reporters/src/getSnapshotSummary.ts` | ソース | スナップショットサマリー生成 |
| getResultHeader.ts | `packages/jest-reporters/src/getResultHeader.ts` | ソース | 結果ヘッダー生成 |
| types.ts | `packages/jest-reporters/src/types.ts` | ソース | 型定義 |
| index.ts | `packages/jest-reporters/src/index.ts` | ソース | エクスポート定義 |
