# 機能設計書 4-予算タイプ設定

## 概要

本ドキュメントは、Actual Budget における予算タイプ（Envelope Budgeting または Tracking Budgeting）の選択・切り替え機能の設計を記述する。ユーザーの予算管理スタイルに応じて、2つの異なる予算方式から選択可能にする。

### 本機能の処理概要

**業務上の目的・背景**：予算管理には複数のアプローチが存在し、ユーザーのニーズや習熟度によって最適な方式は異なる。本機能は、2つの予算タイプを提供することで、初心者からパワーユーザーまで幅広いニーズに対応する。Envelope Budgeting は「使う前に予算を割り当てる」原則に基づき、Tracking Budgeting は月ごとの予算計画と実績追跡に重点を置く。

**機能の利用シーン**：
- 初回セットアップ時に予算タイプを選択する
- 予算管理方式を変更したい場合に設定画面から切り替える
- Envelope方式での厳格な予算管理からTracking方式の柔軟な管理に移行する

**主要な処理内容**：
1. 現在の予算タイプの表示
2. 予算タイプの切り替え（Envelope ⇔ Tracking）
3. 切り替え時の予算キャッシュリセット
4. UIコンポーネントの動的切り替え

**関連システム・外部連携**：設定システム（Synced Prefs）、予算計算エンジン

**権限による制御**：特別な権限制御なし

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 40 | 設定画面 | 主画面 | 封筒予算/追跡予算の切り替え設定 |

## 機能種別

設定変更 / システム切替

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| budgetType | string | Yes | 設定する予算タイプ | 'envelope' または 'tracking' |

### 入力データソース

- 画面入力：設定画面のボタンクリック

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| budgetType | string | 現在の予算タイプ |

### 出力先

- Synced Prefs：予算タイプ設定を保存
- 画面表示：予算画面のUIが切り替わる

## 処理フロー

### 処理シーケンス

```
1. 設定画面で予算タイプ切替ボタンをクリック
   └─ onSwitchType 関数が発火

2. ローディング状態を設定
   └─ setIsLoading(true)

3. 新しい予算タイプを設定
   └─ setBudgetType(newBudgetType)

4. 予算キャッシュをリセット
   └─ send('reset-budget-cache')

5. ローディング状態を解除
   └─ setIsLoading(false)

6. 予算画面が新しいタイプで再描画
   └─ budgetType に基づいてProvider/Componentsが切り替わる
```

### フローチャート

```mermaid
flowchart TD
    A[設定画面表示] --> B[現在の予算タイプ表示]
    B --> C{切替ボタンクリック?}
    C -->|No| D[待機]
    C -->|Yes| E[ローディング開始]
    E --> F{現在のタイプ?}
    F -->|envelope| G[tracking に変更]
    F -->|tracking| H[envelope に変更]
    G --> I[setBudgetType]
    H --> I
    I --> J[reset-budget-cache]
    J --> K[ローディング終了]
    K --> L[UI更新]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-001 | デフォルトタイプ | 初期値は 'envelope' | 新規予算ファイル作成時 |
| BR-002 | キャッシュリセット | タイプ切替時は予算キャッシュをリセット | 切替実行時 |
| BR-003 | 即座反映 | 切替後は予算画面が新タイプで再描画 | 切替完了後 |

### 計算ロジック

Envelope Budgeting の特徴：
- カテゴリ残高が翌月に繰り越される
- 「To Be Budgeted」で未割当予算を管理
- オーバースペンディングの影響がリアルタイムに反映

Tracking Budgeting の特徴：
- カテゴリ残高が月ごとにリセット
- 「Saved」メトリクスで貯蓄状況を管理
- 収入予測に基づいて将来の支出を計画

## データベース操作仕様

### 操作別データベース影響一覧

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| タイプ取得 | prefs | SELECT | budgetType 設定を取得 |
| タイプ設定 | prefs | UPDATE | budgetType 設定を更新 |

### テーブル別操作詳細

#### prefs (Synced Prefs)

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| UPDATE | budgetType | 'envelope' または 'tracking' | 予算タイプ設定 |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| CACHE_RESET_FAILED | システムエラー | キャッシュリセット失敗 | エラーログ出力、再試行 |

### リトライ仕様

- キャッシュリセットは必ず実行される（finally句）

## トランザクション仕様

- 設定変更とキャッシュリセットは順次実行

## パフォーマンス要件

- 切替処理は数秒以内に完了

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

- 設定はローカル/同期設定として保存
- 機密性の高いデータは含まない

## 備考

- 切替により予算データ自体は変更されない（表示・計算方式のみ変更）
- 公式ドキュメントへのリンクを提供

---

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

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

### 推奨読解順序

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

予算タイプの設定保存方法を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | useSyncedPref.ts | `packages/desktop-client/src/hooks/useSyncedPref.ts` | 同期設定フックの仕組み |

**読解のコツ**: `useSyncedPref('budgetType')` で予算タイプ設定を取得・更新する。

#### Step 2: 設定画面を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | BudgetTypeSettings.tsx | `packages/desktop-client/src/components/settings/BudgetTypeSettings.tsx` | 予算タイプ切替UIと処理ロジック |

**主要処理フロー**:
- **15行目**: `useSyncedPref('budgetType')` で現在の設定を取得
- **18-29行目**: `onSwitchType` 関数で切替処理
- **21行目**: 新しいタイプの決定（トグル）
- **22行目**: `setBudgetType` で設定更新
- **25行目**: `send('reset-budget-cache')` でキャッシュリセット

#### Step 3: 予算画面での切替を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | index.tsx | `packages/desktop-client/src/components/budget/index.tsx` | 予算タイプによるProvider/Component切替 |

**主要処理フロー**:
- **53行目**: `useSyncedPref('budgetType')` でタイプ取得
- **156-181行目**: Tracking の場合は `TrackingBudgetProvider` を使用
- **182-207行目**: Envelope の場合は `EnvelopeBudgetProvider` を使用
- **261-267行目**: `useBudgetComponents` でタイプに応じたコンポーネントを取得

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

```
Settings (設定画面)
    │
    └─ BudgetTypeSettings
           │
           ├─ useSyncedPref('budgetType')
           │      └─ 現在の設定を取得
           │
           └─ onSwitchType
                  │
                  ├─ setBudgetType(newType)
                  │      └─ Synced Prefs を更新
                  │
                  └─ send('reset-budget-cache')
                         └─ サーバー側の予算キャッシュをリセット

Budget (予算画面)
    │
    └─ useSyncedPref('budgetType')
           │
           └─ budgetType に基づいて分岐
                  │
                  ├─ 'tracking' → TrackingBudgetProvider
                  │                    └─ TrackingBudgetComponents
                  │
                  └─ 'envelope' → EnvelopeBudgetProvider
                                       └─ EnvelopeBudgetComponents
```

### データフロー図

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

ボタンクリック     ───▶  onSwitchType
(切替要求)                     │
                              ▼
                         setBudgetType           ───▶  Synced Prefs 更新
                              │
                              ▼
                         reset-budget-cache      ───▶  キャッシュクリア
                              │
                              ▼
                         予算画面再描画          ───▶  新しいProvider/Components
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| BudgetTypeSettings.tsx | `packages/desktop-client/src/components/settings/BudgetTypeSettings.tsx` | ソース | 予算タイプ設定UIコンポーネント |
| index.tsx | `packages/desktop-client/src/components/budget/index.tsx` | ソース | 予算画面（タイプによる分岐） |
| EnvelopeBudgetComponents.tsx | `packages/desktop-client/src/components/budget/envelope/EnvelopeBudgetComponents.tsx` | ソース | Envelope用コンポーネント |
| TrackingBudgetComponents.tsx | `packages/desktop-client/src/components/budget/tracking/TrackingBudgetComponents.tsx` | ソース | Tracking用コンポーネント |
| EnvelopeBudgetContext.tsx | `packages/desktop-client/src/components/budget/envelope/EnvelopeBudgetContext.tsx` | ソース | Envelope用Context |
| TrackingBudgetContext.tsx | `packages/desktop-client/src/components/budget/tracking/TrackingBudgetContext.tsx` | ソース | Tracking用Context |
| useSyncedPref.ts | `packages/desktop-client/src/hooks/useSyncedPref.ts` | ソース | 同期設定フック |
