# 通知設計書 30-コンパイルエラー通知

## 概要

本ドキュメントは、Next.js開発サーバーにおけるコンパイルエラー通知の設計を記述する。コンパイルエラーが発生した際にコンソールへエラーメッセージを出力し、開発者にコンパイル失敗の原因を通知する仕組みについて定義する。

### 本通知の処理概要

開発サーバーのコンパイルプロセスでエラーが発生した場合、`OutputState`のstoreの`errors`フィールドにエラーメッセージが格納され、storeサブスクリプションを通じてコンソールへエラーメッセージを出力する。

**業務上の目的・背景**：開発中のコンパイルエラー（構文エラー、型エラー、モジュール解決エラー等）をターミナルに即座に表示することで、開発者がブラウザを確認することなくエラーの原因を把握し、迅速に修正を行えるようにする。ブラウザ側のDev Overlayでもエラーが表示されるが、ターミナルへの出力は開発者のワークフローにおける重要なフィードバックチャネルである。

**通知の送信タイミング**：`OutputState`のstoreが`loading: false`かつ`errors`がnon-nullに更新された時点で、storeサブスクリプションを通じて即座にコンソールへ出力される。

**通知の受信者**：開発者のターミナル（コンソール出力）。

**通知内容の概要**：エラーメッセージの最初の1件（`state.errors[0]`）が`Log.error()`で出力される。エラーメッセージにはコンパイラが生成したエラー詳細（ファイルパス、行番号、エラー内容等）が含まれる。

**期待されるアクション**：開発者はエラーメッセージを確認し、該当するソースコードを修正する。修正後、ファイル保存により再コンパイルが自動的にトリガーされる。

## 通知種別

コンソールメッセージ（ターミナル出力）

## 送信仕様

### 基本情報

| 項目 | 内容 |
|-----|------|
| 送信方式 | 同期（storeサブスクリプション内で即座に出力） |
| 優先度 | 高（エラーは即座に出力される） |
| リトライ | なし |

### 送信先決定ロジック

`store`のstateサブスクリプション内で、`state.errors`が存在する場合に`Log.error(state.errors[0])`で最初のエラーメッセージを出力する。

## 通知テンプレート

### メール通知の場合

該当なし（コンソールメッセージのため）

### 本文テンプレート

```
✕ ./app/page.tsx
Module not found: Can't resolve './missing-module'

https://nextjs.org/docs/messages/module-not-found
```

### 添付ファイル

該当なし

## テンプレート変数

| 変数名 | 説明 | データ取得元 | 必須 |
|--------|------|-------------|-----|
| errors[0] | 最初のコンパイルエラーメッセージ | `state.errors[0]`（string型） | Yes |

## 送信トリガー・条件

### トリガー一覧

| トリガー種別 | トリガーイベント | 送信条件 | 説明 |
|------------|----------------|---------|------|
| サーバーイベント | OutputStateが`errors`非nullに変化 | `state.errors`が存在 | コンパイルエラー発生時 |

### 送信抑止条件

| 条件 | 説明 |
|-----|------|
| `logging === false` | ログ出力が無効化されている場合 |
| 状態未変更 | `hasStoreChanged`がfalseを返す場合 |
| `bootstrap === true` | サーバー起動前のブートストラップ状態 |
| `state.loading === true` | コンパイル中の場合はエラー出力しない |

## 処理フロー

### 送信フロー

```mermaid
flowchart TD
    A[OutputState更新: errors非null] --> B{logging有効?}
    B -->|No| C[出力スキップ]
    B -->|Yes| D{状態変化あり?}
    D -->|No| C
    D -->|Yes| E{bootstrap?}
    E -->|Yes| C
    E -->|No| F{loading?}
    F -->|Yes| G[loadingハンドリング]
    F -->|No| H{errorsあり?}
    H -->|Yes| I[Log.error state.errors/0/]
    H -->|No| J[その他の処理]
    I --> K[startTime = 0 リセット]
    K --> L[flushAllTraces]
    L --> M[teardownTraceSubscriber]
```

## データベース参照・更新仕様

### 参照テーブル一覧

該当なし

### 更新テーブル一覧

該当なし

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 対処方法 |
|----------|---------|---------|
| 該当なし | コンソール出力のみのため、エラーケースは存在しない | - |

### リトライ仕様

| 項目 | 内容 |
|-----|------|
| リトライ回数 | なし |
| リトライ間隔 | 該当なし |
| リトライ対象エラー | 該当なし |

## 配信設定

### レート制限

| 項目 | 内容 |
|-----|------|
| 1分あたり上限 | 制限なし |
| 1日あたり上限 | 制限なし |

### 配信時間帯

制限なし（開発サーバー稼働中は常時出力可能）

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

本通知はローカル開発環境専用のコンソールメッセージ。エラーメッセージにはファイルパスやソースコードの断片が含まれる可能性があるが、開発環境のみで使用されるためリスクは低い。

## 備考

- エラーメッセージは最初の1件のみ出力される（`state.errors[0]`）。複数のエラーがある場合でも、コンソールには最初のエラーのみが表示される。
- エラー発生時に`startTime`が0にリセットされ、コンパイル時間の計測がキャンセルされる。
- `flushAllTraces()`と`teardownTraceSubscriber()`によりトレース情報がフラッシュされる。
- コンパイルエラーはブラウザ側ではBUILT/SYNCメッセージの`errors`フィールドとしても送信され、Dev Overlayに表示される（別通知：No.17/No.18参照）。

---

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

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

### 推奨読解順序

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | store.ts | `packages/next/src/build/output/store.ts` | 8-34行目: `OutputState`型定義。`loading: false`の場合の`errors: string[] \| null`フィールドを確認 |

**読解のコツ**: `errors`はstring型の配列またはnull。nullの場合はエラーなし、非nullの場合は1つ以上のエラーが存在する。

#### Step 2: エラー出力ロジックを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | store.ts | `packages/next/src/build/output/store.ts` | 133-141行目: `state.errors`がtruthyの場合の処理。`Log.error(state.errors[0])`で最初のエラーを出力し、`startTime`をリセット、トレースをフラッシュ |

**主要処理フロー**:
1. **84行目**: `store.subscribe(state => { ... })`でstateの変更を監視
2. **133行目**: `if (state.errors)`の条件判定
3. **135行目**: `Log.error(state.errors[0])`で最初のエラーメッセージを出力
4. **137行目**: `startTime = 0`でコンパイル時間計測をリセット
5. **139行目**: `flushAllTraces()`でトレース情報をフラッシュ
6. **140行目**: `teardownTraceSubscriber()`でトレースサブスクライバーをクリーンアップ

#### Step 3: エラー状態の設定元を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | hot-reloader-turbopack.ts | `packages/next/src/server/dev/hot-reloader-turbopack.ts` | 413-444行目: `startBuilding`関数内で`consoleStore.setState`を呼び出し。`loading: false`への遷移時にエラー情報が設定される |

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

```
consoleStore.setState({ loading: false, errors: [...], ... }) [呼び出し元]
    |
    +-- store.subscribe(state => { ... }) [store.ts:84]
           |
           +-- hasStoreChanged(state) [store.ts:62]
           +-- [state.errors] Log.error(state.errors[0]) [store.ts:135]
           +-- startTime = 0 [store.ts:137]
           +-- flushAllTraces() [store.ts:139]
           +-- teardownTraceSubscriber() [store.ts:140]
```

### データフロー図

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

consoleStore.setState({    ──> store.subscribe()                ──> ターミナルコンソール
  loading: false,                state.errors判定                    "✕ エラーメッセージ..."
  errors: ["..."],               Log.error(errors[0])
  ...                            トレースフラッシュ
})
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| store.ts | `packages/next/src/build/output/store.ts` | ソース | OutputState管理、コンソール出力ロジック |
| log.ts | `packages/next/src/build/output/log.ts` | ソース | Log.error等のコンソール出力ユーティリティ |
| hot-reloader-turbopack.ts | `packages/next/src/server/dev/hot-reloader-turbopack.ts` | ソース | consoleStore.setState呼び出し元 |
| index.ts | `packages/next/src/build/output/index.ts` | ソース | コンパイラ監視とstore更新 |
