# 機能設計書 77-setup_zshrc

## 概要

本ドキュメントは、Oh My Zshインストールスクリプト（tools/install.sh）内の`setup_zshrc`関数の機能設計について記述する。

### 本機能の処理概要

`setup_zshrc`関数は、Oh My Zsh用の.zshrcファイルを作成する処理を担当する。既存の.zshrcファイルが存在する場合はバックアップを作成し、テンプレートファイル（templates/zshrc.zsh-template）から新しい.zshrcを生成する。$ZSHパスをテンプレート内で適切に置換し、ポータブルな設定ファイルを作成する。

**業務上の目的・背景**：Oh My Zshを使用するには、.zshrcファイルに適切な初期化コードを記述する必要がある。本関数は、ユーザーの既存設定を破壊することなく、Oh My Zsh用の標準的な.zshrcを自動的に設定する。これにより、インストール直後からOh My Zshの機能を利用できる。

**機能の利用シーン**：
- install.shによるOh My Zshの新規インストール時
- 既存の.zshrcを保持したい場合（KEEP_ZSHRC=yes）
- 上書き確認をスキップしたい場合（OVERWRITE_CONFIRMATION=no）

**主要な処理内容**：
1. 既存.zshrcの存在確認
2. KEEP_ZSHRC=yesの場合は処理をスキップ
3. OVERWRITE_CONFIRMATION=yesの場合は上書き確認ダイアログを表示
4. 既存.zshrcを.zshrc.pre-oh-my-zshにバックアップ
5. 古いバックアップが存在する場合はタイムスタンプ付きでさらにバックアップ
6. テンプレートから$ZSH変数を適切に置換して.zshrcを生成

**関連システム・外部連携**：ファイルシステム操作（mv、sed、cat）。

**権限による制御**：ユーザーのホームディレクトリ（または$ZDOTDIR）に書き込み権限が必要。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 17 | install.sh | 主画面 | Oh My Zshインストールの一部として.zshrcを設定 |

## 機能種別

ファイル生成・バックアップ

## 入力仕様

### 入力パラメータ

setup_zshrc関数自体は引数を取らないが、以下のグローバル変数を参照する。

| 変数名 | 型 | 必須 | 説明 |
|--------|-----|-----|------|
| $ZSH | string | Yes | Oh My Zshインストールディレクトリ |
| $zdot | string | Yes | .zshrcの配置先ディレクトリ（$ZDOTDIRまたは$HOME） |
| $ZDOTDIR | string | No | Zsh dotfilesディレクトリ（設定時） |
| $HOME | string | Yes | ユーザーのホームディレクトリ |
| $KEEP_ZSHRC | string | No | "yes"で既存.zshrcを保持 |
| $OVERWRITE_CONFIRMATION | string | No | "no"で上書き確認をスキップ |

### 入力データソース

- グローバル変数（install.shで設定）
- 既存の.zshrcファイル（存在する場合）
- テンプレートファイル（templates/zshrc.zsh-template）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| .zshrc | file | Oh My Zsh設定を含むzsh設定ファイル |
| .zshrc.pre-oh-my-zsh | file | バックアップされた元の.zshrc（存在した場合） |
| .zshrc.pre-oh-my-zsh-YYYY-MM-DD_HH-MM-SS | file | 古いバックアップのタイムスタンプ付きコピー |

### 出力先

- $zdot（$ZDOTDIRまたは$HOME）

## 処理フロー

### 処理シーケンス

```
1. 開始メッセージ表示
   └─ "Looking for an existing zsh config..."
2. 既存.zshrc確認
   └─ if [ -f "$zdot/.zshrc" ] || [ -h "$zdot/.zshrc" ]
3. KEEP_ZSHRC確認
   └─ yesの場合はスキップ
4. 上書き確認（OVERWRITE_CONFIRMATION != no時）
   └─ minimal.zshrcを表示して確認
   └─ Y/yまたはEnterで続行、N/nでスキップ
5. 既存バックアップ確認
   └─ .zshrc.pre-oh-my-zsh存在時はタイムスタンプ付きでバックアップ
6. .zshrcバックアップ
   └─ mv "$zdot/.zshrc" "$OLD_ZSHRC"
7. テンプレートから.zshrc生成
   └─ $ZSHを$ZDOTDIR/または$HOME/で置換
   └─ sed で置換してコピー
```

### フローチャート

```mermaid
flowchart TD
    A[setup_zshrc開始] --> B{既存.zshrc存在?}
    B -->|No| C[テンプレートからコピー]
    B -->|Yes| D{KEEP_ZSHRC=yes?}
    D -->|Yes| E["Keeping..." 表示して終了]
    D -->|No| F{OVERWRITE_CONFIRMATION=no?}
    F -->|No| G[上書き確認ダイアログ]
    G --> H{Y/Enter?}
    H -->|No| I[スキップして終了]
    H -->|Yes| J[バックアップ処理へ]
    F -->|Yes| J
    J --> K{既存バックアップ存在?}
    K -->|Yes| L[タイムスタンプ付きで移動]
    K -->|No| M[.zshrcをバックアップ]
    L --> M
    M --> C
    C --> N[$ZSH変数を置換]
    N --> O[.zshrc生成完了]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-77-01 | バックアップ必須 | 既存.zshrcは必ずバックアップ | 既存.zshrc存在時 |
| BR-77-02 | バックアップ命名 | バックアップファイル名は.zshrc.pre-oh-my-zsh | 常時 |
| BR-77-03 | 二重バックアップ | 既存バックアップはタイムスタンプ付きで保存 | 既存バックアップ存在時 |
| BR-77-04 | 確認スキップ | KEEP_ZSHRC=yesで処理全体をスキップ | KEEP_ZSHRC設定時 |
| BR-77-05 | パス置換 | $ZSHを$ZDOTDIR/または$HOME/で始まる形式に変換 | テンプレート処理時 |

### 計算ロジック

```
# $ZSH変数の置換ロジック
if ZDOTDIR設定 && ZDOTDIR != HOME:
    omz = $ZSH.replace($ZDOTDIR, "$ZDOTDIR")
omz = omz.replace($HOME, "$HOME")
```

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

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

データベース操作なし

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| 1 | バックアップ衝突 | タイムスタンプ付きバックアップが既に存在 | 数秒待ってから再実行 |

### リトライ仕様

バックアップ衝突時は再実行を促すメッセージを表示

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

- バックアップ処理は順次実行
- 中間状態での中断時は手動で復旧が必要

## パフォーマンス要件

即時完了（ファイル操作のみ）

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

- 既存.zshrcの内容は保持（バックアップ）
- ユーザーの確認なしに上書きしない（デフォルト）
- minimal.zshrcを表示して必要最小限の設定を示す

## 備考

- uninstall.shは.zshrc.pre-oh-my-zshを使用して元の.zshrcを復元する
- テンプレートファイルの$ZSH変数行のみを置換するため、他の設定は保持される
- シンボリックリンクの.zshrcも適切に処理される

---

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

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

### 推奨読解順序

#### Step 1: 関数の全体構造を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | install.sh | `tools/install.sh` | setup_zshrc関数の定義（332-394行目） |

**読解のコツ**: POSIXシェル互換スクリプト。`[ -f ... ] || [ -h ... ]`はファイルまたはシンボリックリンクの存在確認。`read -r opt`で1行入力を受け取る。

**主要処理フロー**:
- **336行目**: "Looking for an existing zsh config..." メッセージ
- **339行目**: `OLD_ZSHRC="$zdot/.zshrc.pre-oh-my-zsh"` バックアップファイル名設定
- **340行目**: 既存.zshrc存在確認
- **342-345行目**: KEEP_ZSHRC=yes時のスキップ処理
- **347-363行目**: 上書き確認ダイアログ
- **365-376行目**: 既存バックアップのタイムスタンプ付き移動
- **377-378行目**: .zshrcのバックアップ
- **381-391行目**: テンプレートからの.zshrc生成

#### Step 2: 上書き確認ダイアログを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | install.sh | `tools/install.sh` | 上書き確認ダイアログ（347-363行目） |

**主要処理フロー**:
- **347行目**: `if [ $OVERWRITE_CONFIRMATION != "no" ]` 確認が必要か判定
- **349-352行目**: 警告メッセージとminimal.zshrc表示
- **353行目**: `cat "$ZSH/templates/minimal.zshrc"` 最小設定例を表示
- **355-356行目**: 確認プロンプト
- **357-362行目**: case文で入力判定（Y/y/Enter: 続行、N/n: スキップ）

#### Step 3: テンプレート処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | install.sh | `tools/install.sh` | テンプレート処理（384-391行目） |

**主要処理フロー**:
- **384行目**: `omz="$ZSH"` 置換用変数初期化
- **385-386行目**: ZDOTDIR設定時の置換（`$ZDOTDIR/`形式に）
- **388行目**: HOME設定時の置換（`$HOME/`形式に）
- **390行目**: `sed "s|^export ZSH=.*$|export ZSH=\"${omz}\"|"` テンプレート内の$ZSH行を置換
- **391行目**: 一時ファイルを最終ファイルにリネーム

#### Step 4: テンプレートファイルを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | zshrc.zsh-template | `templates/zshrc.zsh-template` | .zshrcテンプレート |
| 4-2 | minimal.zshrc | `templates/minimal.zshrc` | 最小設定例 |

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

```
setup_zshrc() (tools/install.sh:332-394)
    │
    ├─ [ -f "$zdot/.zshrc" ] (既存.zshrc確認)
    │
    ├─ [KEEP_ZSHRC=yes] ──▶ return (スキップ)
    │
    ├─ [OVERWRITE_CONFIRMATION != no]
    │      │
    │      ├─ cat "$ZSH/templates/minimal.zshrc"
    │      │
    │      └─ read -r opt (ユーザー入力)
    │
    ├─ mv "$OLD_ZSHRC" "${OLD_OLD_ZSHRC}" (二重バックアップ)
    │
    ├─ mv "$zdot/.zshrc" "$OLD_ZSHRC" (バックアップ)
    │
    ├─ sed "s|^export ZSH=.*$|...|" (置換)
    │      │
    │      └─ $ZSH/templates/zshrc.zsh-template ──▶ $zdot/.zshrc-omztemp
    │
    └─ mv "$zdot/.zshrc-omztemp" "$zdot/.zshrc"
```

### データフロー図

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

既存.zshrc ─────────────▶ mv ─────────────────────────▶ .zshrc.pre-oh-my-zsh
                                                        (バックアップ)
                              │
既存バックアップ ─────────────┼───▶ mv ──────────────▶ .zshrc.pre-oh-my-zsh-*
                              │                        (タイムスタンプ付き)
                              │
$ZSH変数 ─────────────────────┤
$ZDOTDIR ─────────────────────┼───▶ sed (置換処理)
$HOME ────────────────────────┤
                              │
テンプレート ─────────────────┴───▶ 一時ファイル ──▶ mv ──▶ .zshrc
(zshrc.zsh-template)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| install.sh | `tools/install.sh` | ソース | setup_zshrc関数の定義元 |
| zshrc.zsh-template | `templates/zshrc.zsh-template` | テンプレート | .zshrcのテンプレート |
| minimal.zshrc | `templates/minimal.zshrc` | テンプレート | 最小限の.zshrc設定例（確認ダイアログで表示） |
| uninstall.sh | `tools/uninstall.sh` | ソース | .zshrc.pre-oh-my-zshを使用して復元 |
