# 帳票設計書 2-Stats テキストレポート

## 概要

本ドキュメントは、webpackのビルド結果統計情報をテキスト形式で出力する「Stats テキストレポート」の設計仕様を定義する。

### 本帳票の処理概要

Stats テキストレポートは、webpackのビルド（コンパイル）結果に関する統計情報を人間が読みやすいテキスト形式でフォーマットして出力する帳票である。`Stats.toString()` メソッドを呼び出すことで、ビルドサマリー、アセット一覧、モジュール一覧、チャンク情報、エラー・警告メッセージなどがコンソール出力に適した形式で整形される。

**業務上の目的・背景**：ビルド結果を開発者が素早く確認できるようにするために必要である。JSON出力とは異なり、色付け、インデント、サイズの人間可読フォーマット（KiB, MiB等）、フラグ表示（emitted, cached等）を含むテキスト出力を提供し、コンソール上での視認性を高める。

**帳票の利用シーン**：webpack CLIの通常実行時のコンソール出力、webpack-dev-serverのビルド結果表示、ビルドスクリプトのログ出力に利用される。

**主要な出力内容**：
1. ビルドサマリー（バージョン、ハッシュ、ビルド時間、成功/失敗状態）
2. アセット一覧（ファイル名、サイズ、emitted/cached状態）
3. モジュール一覧（名前、サイズ、依存関係）
4. チャンク情報（ID、名前、サイズ）
5. エントリーポイント・チャンクグループ
6. エラー・警告メッセージ（色付き出力）
7. ロギング情報

**帳票の出力タイミング**：ビルド完了後、`Stats.toString(options)` メソッドの呼び出し時に生成される。webpack CLIの通常実行時に自動的に呼び出される。

**帳票の利用者**：フロントエンド開発者、ビルドログの閲覧者。

## 帳票種別

テキスト出力（コンソール出力）

## 利用画面

| 画面No | 画面名 | URL/ルーティング | 出力操作 |
|--------|--------|-----------------|---------|
| - | CLI | `webpack` | 通常実行（`--json` なし） |
| - | Node.js API | プログラム内呼び出し | `stats.toString(options)` メソッド呼び出し |

## 出力形式

### 基本仕様

| 項目 | 内容 |
|-----|------|
| ファイル形式 | プレーンテキスト（ANSIカラーコード付き） |
| 用紙サイズ | N/A（コンソール出力） |
| 向き | N/A |
| ファイル名 | N/A（標準出力） |
| 出力方法 | 標準出力（console） |
| 文字コード | UTF-8 |

## 帳票レイアウト

### レイアウト概要

テキストレポートは、StatsPrinterによりStatsCompilationオブジェクトの各フィールドを文字列に変換し、改行で結合して出力する。

```
┌─────────────────────────────────────┐
│   サマリー行（バージョン・ハッシュ・時間） │
├─────────────────────────────────────┤
│   アセット一覧                        │
│   エントリーポイント                    │
│   チャンクグループ                     │
├─────────────────────────────────────┤
│   モジュール一覧                      │
├─────────────────────────────────────┤
│   エラー・警告メッセージ                │
│   子コンパイル情報                     │
└─────────────────────────────────────┘
```

### ヘッダー部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | compilation.summary! | ビルドサマリー行 | StatsCompilation | `{builtAt}: {name} (webpack {version}) compiled {status} in {time} ({hash})` |

### 明細部

| No | 項目名 | 説明 | データ取得元 | 表示形式 | 列幅 |
|----|-------|------|-------------|---------|-----|
| 1 | asset.name | アセットファイル名 | StatsAsset.name | formatFilename() | - |
| 2 | asset.size | アセットサイズ | StatsAsset.size | formatSize()（KiB, MiB等） | - |
| 3 | asset.emitted | 出力済みフラグ | StatsAsset.emitted | `[emitted]`（緑色） | - |
| 4 | asset.cached | キャッシュフラグ | StatsAsset.cached | `[cached]`（緑色） | - |
| 5 | module.name | モジュール名 | StatsModule.name | prefix + bold(resource) | - |
| 6 | module.sizes | モジュールサイズ | StatsModule.sizes | formatSize() | - |
| 7 | module.id | モジュールID | StatsModule.id | formatModuleId() | - |
| 8 | chunk.id | チャンクID | StatsChunk.id | formatChunkId() | - |

### フッター部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | filteredModules | フィルタ済みモジュール数 | StatsCompilation.filteredModules | `+ N modules` |
| 2 | filteredAssets | フィルタ済みアセット数 | StatsCompilation.filteredAssets | `+ N assets` |
| 3 | warningsInChildren | 子コンパイルの警告数 | warningsCount - warnings.length | 黄色テキスト |
| 4 | errorsInChildren | 子コンパイルのエラー数 | errorsCount - errors.length | 赤色テキスト |

## 出力条件

### 抽出条件

| 条件名 | 説明 | 必須 |
|-------|------|-----|
| StatsOptions | stats設定オブジェクト | No（デフォルト値あり） |
| forToString | true固定（テキスト出力時） | Yes（内部設定） |

### ソート順

| 優先度 | 項目 | 昇順/降順 |
|-------|------|---------|
| 1 | elements | sortElements フックによるカスタム順序 |
| 2 | items | sortItems フックによるカスタム順序 |

### 改ページ条件

N/A（テキスト出力のため改ページなし）

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

### 参照テーブル一覧

本帳票はデータベースを参照しない。Stats JSON レポート（No.1）で生成されたStatsCompilationオブジェクトを入力として受け取る。

| テーブル名 | 用途 | 結合条件 |
|-----------|------|---------|
| StatsCompilation | JSON形式の統計データ | Stats.toJson()の出力 |

## 計算仕様

### 計算項目一覧

| 項目名 | 計算式 | 端数処理 | 備考 |
|-------|-------|---------|------|
| childWarnings | warningsCount - warnings.length | なし | 子コンパイルの警告数 |
| childErrors | errorsCount - errors.length | なし | 子コンパイルのエラー数 |

## 処理フロー

### 出力フロー

```mermaid
flowchart TD
    A[Stats.toString呼び出し] --> B[createStatsOptions でオプション正規化 forToString:true]
    B --> C[createStatsFactory でStatsFactory生成]
    C --> D[createStatsPrinter でStatsPrinter生成]
    D --> E[statsFactory.create でStatsCompilation JSON生成]
    E --> F[statsPrinter.print でテキスト変換]
    F --> G{オブジェクト型?}
    G -->|Yes| H[各要素をprint→printElements]
    G -->|No 配列| I[各アイテムをprint→printItems]
    H --> J[結果文字列を返却]
    I --> J
```

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 表示メッセージ | 対処方法 |
|----------|---------|--------------|---------|
| データなし | printResultがundefined | 空文字列を返却 | Stats.toString() 行85で空文字にフォールバック |
| 不正オプション | StatsOptionsが不正 | 内部でデフォルト値にフォールバック | 正しいStatsOptions形式で指定 |

## パフォーマンス要件

| 項目 | 内容 |
|-----|------|
| 想定データ件数 | モジュール数千〜数万 |
| 目標出力時間 | JSON生成 + テキスト変換のため、JSON出力の約1.5〜2倍 |
| 同時出力数上限 | 1（シングルスレッド処理） |

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

テキスト出力にはファイルパス情報が含まれる。`makePathsRelative` によるパスの相対化、`getModuleName` によるモジュール名の切り詰め（80文字上限）が行われる。コンソール出力はログファイルに保存される可能性があるため注意。

## 備考

- テキスト出力はJSON出力の全工程に加え、StatsPrinterによるテキスト変換工程が追加される
- ANSIカラーコードによる色付け（bold, yellow, red, green, magenta, cyan）が利用可能
- `compilation.summary!` はStatsPrinterの特殊プリンターで、サマリー行を生成する

---

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

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

### 推奨読解順序

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

テキスト出力の元となるStatsCompilationデータ構造と、StatsPrinterContextの型定義を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | StatsPrinter.js | `lib/stats/StatsPrinter.js` | 行23-73: `KnownStatsPrinterContext`, `KnownStatsPrinterColorFunctions`, `KnownStatsPrinterFormatters` の型定義を読み、プリンターコンテキストの構造を把握する |

**読解のコツ**: `StatsPrinterContext` にはカラー関数（bold, red等）とフォーマッター関数（formatSize, formatFilename等）が含まれる。

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

処理の起点となる `Stats.toString()` メソッドを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | Stats.js | `lib/Stats.js` | 行73-86: `toString()` メソッドがStatsFactory + StatsPrinterを生成し、JSON化→テキスト化の2段階処理を行う |

**主要処理フロー**:
1. **行74-76**: `createStatsOptions` でオプション正規化（`forToString: true`）
2. **行78**: `createStatsFactory` でStatsFactory生成
3. **行79**: `createStatsPrinter` でStatsPrinter生成
4. **行81-83**: `statsFactory.create` でJSON生成
5. **行84**: `statsPrinter.print` でテキスト変換
6. **行85**: 結果がundefinedなら空文字を返却

#### Step 3: StatsPrinterのテキスト変換パイプラインを理解する

StatsPrinterの `print` / `_print` メソッドがテキスト変換の中核。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | StatsPrinter.js | `lib/stats/StatsPrinter.js` | 行184-297: `print` メソッドと `_print` メソッド。hooks.print→配列処理orオブジェクト処理→hooks.result の流れ |

**主要処理フロー**:
- **行213-215**: `hooks.print` でカスタムプリントを試行
- **行217-251**: 配列の場合: sortItems → getItemName → 再帰print → printItems
- **行256-286**: オブジェクトの場合: sortElements → 各要素をprint → printElements

#### Step 4: DefaultStatsPrinterPluginのフォーマットロジックを理解する

実際のテキストフォーマット処理を行う各種SimplePrintersを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | DefaultStatsPrinterPlugin.js | `lib/stats/DefaultStatsPrinterPlugin.js` | 行196-406: `COMPILATION_SIMPLE_PRINTERS` - compilationレベルのプリンター |
| 4-2 | DefaultStatsPrinterPlugin.js | `lib/stats/DefaultStatsPrinterPlugin.js` | 行418-467: `ASSET_SIMPLE_PRINTERS` - アセットのプリンター |
| 4-3 | DefaultStatsPrinterPlugin.js | `lib/stats/DefaultStatsPrinterPlugin.js` | 行477-500: `MODULE_SIMPLE_PRINTERS` - モジュールのプリンター |

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

```
Stats.toString(options)
    |
    +-- compilation.createStatsOptions(options, { forToString: true })
    +-- compilation.createStatsFactory(normalizedOptions)
    +-- compilation.createStatsPrinter(normalizedOptions)
    |
    +-- statsFactory.create("compilation", compilation, context)
    |       |  (No.1 Stats JSON レポートと同一の処理)
    |       +-- SIMPLE_EXTRACTORS.compilation.*()
    |
    +-- statsPrinter.print("compilation", data)
            |
            +-- hooks.print ("compilation")
            +-- _print("compilation", StatsCompilation)
                    |
                    +-- sortElements
                    +-- print("compilation.summary!", ...)
                    |       +-- COMPILATION_SIMPLE_PRINTERS["compilation.summary!"]
                    +-- print("compilation.assets", ...)
                    |       +-- ASSET_SIMPLE_PRINTERS["asset.name"]
                    |       +-- ASSET_SIMPLE_PRINTERS["asset.size"]
                    +-- print("compilation.modules", ...)
                    |       +-- MODULE_SIMPLE_PRINTERS["module.name"]
                    |       +-- MODULE_SIMPLE_PRINTERS["module.sizes"]
                    +-- print("compilation.errors", ...)
                    +-- print("compilation.warnings", ...)
                    +-- printElements
```

### データフロー図

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

Compilation        -->  Stats.toString()                -->  テキスト文字列
                   -->    StatsFactory.create()         -->    StatsCompilation (中間JSON)
                   -->    StatsPrinter.print()          -->    フォーマット済みテキスト
                   -->      COMPILATION_SIMPLE_PRINTERS -->      サマリー行
                   -->      ASSET_SIMPLE_PRINTERS       -->      アセット一覧
                   -->      MODULE_SIMPLE_PRINTERS      -->      モジュール一覧
                   -->      hooks.result                -->      最終テキスト
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| Stats.js | `lib/Stats.js` | ソース | エントリーポイント。toString()メソッドを提供 |
| StatsFactory.js | `lib/stats/StatsFactory.js` | ソース | JSON中間データ生成 |
| StatsPrinter.js | `lib/stats/StatsPrinter.js` | ソース | テキスト変換パイプラインを管理 |
| DefaultStatsFactoryPlugin.js | `lib/stats/DefaultStatsFactoryPlugin.js` | ソース | データ抽出ロジック |
| DefaultStatsPrinterPlugin.js | `lib/stats/DefaultStatsPrinterPlugin.js` | ソース | テキストフォーマット定義（COMPILATION/ASSET/MODULE_SIMPLE_PRINTERS） |
| Compilation.js | `lib/Compilation.js` | ソース | ビルド結果を保持するコンパイルオブジェクト |
