# 機能設計書 81-カレンダー統合

## 概要

本ドキュメントは、Doom Emacsにおけるカレンダー統合機能（`modules/app/calendar/`）の設計を記述する。この機能は、calfwパッケージを使用して視覚的なカレンダーインターフェースを提供し、org-mode、iCal、Google Calendarなど様々なカレンダーソースと統合する。

### 本機能の処理概要

**業務上の目的・背景**：現代の開発者やナレッジワーカーは、スケジュール管理とコーディング作業を同一環境で行うことで効率を向上させたいというニーズがある。本機能は、Emacsから離れることなくカレンダーを確認・操作できる環境を提供し、コンテキストスイッチのコストを削減する。特にorg-agendaとの連携により、タスク管理とスケジュール管理をシームレスに統合できる。

**機能の利用シーン**：
- 日次・週次のスケジュール確認時
- org-agendaの予定をカレンダービューで俯瞰したい場合
- 外部カレンダー（Google Calendar、iCal）との同期が必要な場合
- ワークスペース機能を活用した専用カレンダー環境での作業時

**主要な処理内容**：
1. `=calendar`コマンドによる専用ワークスペースでのカレンダー起動
2. calfwを使用した月次/週次/日次ビューの表示
3. org-mode予定との統合表示（calfw-org）
4. iCal/icalendarフォーマットのカレンダー読み込み（calfw-ical）
5. Emacs標準diary形式との連携（calfw-cal）
6. Google Calendar同期（org-gcal）
7. Evil/Vimキーバインドによる効率的なナビゲーション

**関連システム・外部連携**：
- org-mode: org-agendaファイルからの予定読み込み
- Google Calendar: org-gcalパッケージ経由でのOAuth2認証・同期
- iCal: RFC 5545形式のカレンダーファイル読み込み
- Emacs diary: 標準diary形式のサポート

**権限による制御**：Google Calendar連携時はOAuth2トークンが必要。トークンファイルは`doom-profile-cache-dir`に暗号化して保存される（org-gcal-token-file）。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 14 | Calendar | 主画面 | calfwによるカレンダー表示、予定表示 |

## 機能種別

表示・ナビゲーション / 外部データ連携

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| +calendar-open-function | function | No | カレンダーを開く際に呼び出される関数 | callable function |
| +calendar-workspace-name | string | No | カレンダー専用ワークスペースの名前（デフォルト: "*calendar*"） | 文字列 |

### 入力データソース

- org-agendaファイル（org-mode予定）
- iCalファイル（URLまたはローカルファイル）
- Emacs diaryファイル
- Google Calendar API（OAuth2認証経由）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| カレンダーバッファ | buffer | calfwカレンダービューを表示するバッファ |
| 詳細バッファ | buffer | 選択した予定の詳細を表示するポップアップバッファ |

### 出力先

- *calfw-calendar*バッファ: メインカレンダービュー
- *calfw-details*バッファ: 予定詳細ポップアップ（サイズ0.4、自動終了）

## 処理フロー

### 処理シーケンス

```
1. =calendar コマンド実行
   └─ ワークスペースモジュールの有無を確認
2. ワークスペース切り替え/作成
   └─ +calendar-workspace-name で指定された名前のワークスペースに切り替え
3. カレンダーバッファの存在確認
   └─ 既存バッファがあれば選択、なければ新規作成
4. +calendar--init 呼び出し
   └─ calfw の require と +calendar-open-function の実行
5. calfw-org-open-calendar でカレンダー表示
   └─ org-agendaをソースとしたカレンダービュー生成
6. Evil キーバインド設定（オプション）
   └─ evil モジュールが有効な場合、motion state で操作可能に
```

### フローチャート

```mermaid
flowchart TD
    A[=calendar 実行] --> B{workspaces モジュール有効?}
    B -->|Yes| C[専用ワークスペースに切り替え]
    B -->|No| D[現在のウィンドウ設定を保存]
    C --> E{カレンダーバッファ存在?}
    D --> F[他ウィンドウを削除]
    E -->|Yes| G[既存バッファを選択]
    E -->|No| H[スクラッチバッファに切り替え]
    F --> H
    G --> I[ワークスペース表示]
    H --> J[+calendar--init 実行]
    J --> K[calfw require]
    K --> L[+calendar-open-function 実行]
    L --> M[calfw-org-open-calendar]
    M --> N[カレンダービュー表示]
    I --> N
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-01 | ワークスペース分離 | カレンダーは専用ワークスペースで管理し、他の作業と分離する | workspacesモジュール有効時 |
| BR-02 | ウィンドウ設定復元 | カレンダー終了時は元のウィンドウレイアウトを復元する | workspacesモジュール無効時 |
| BR-03 | バッファクリーンアップ | カレンダー終了時は関連バッファ（*cfw[-:]で始まるもの）をすべて削除する | 常時 |
| BR-04 | モードライン非表示 | カレンダーバッファではモードラインを非表示にする | 常時 |

### 計算ロジック

なし

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

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

本機能はデータベースを直接操作しない。データは外部ソース（org-files、iCal、Google Calendar API）から取得する。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| N/A | org-gcal認証エラー | Google Calendar OAuth2トークンが無効または期限切れ | org-gcal-token-fileを削除して再認証 |
| N/A | iCal読み込みエラー | iCalファイルが見つからないまたは形式不正 | URLまたはファイルパスを確認 |
| N/A | org-agenda未設定 | org-agenda-filesが空 | org-agenda-filesを設定 |

### リトライ仕様

iCalの外部URL取得時は標準のurl.elの再試行メカニズムに依存する。

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

該当なし（読み取り専用操作が主）

## パフォーマンス要件

- カレンダー初期表示: 1秒以内（ローカルソースのみの場合）
- org-agenda統合: org-agenda-filesの数に依存
- 外部iCal取得: ネットワーク環境に依存

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

- Google Calendarトークンは`org-gcal-token-file`に保存され、GPG暗号化推奨（.gpg拡張子）
- 外部iCal URLからの読み込み時はHTTPS推奨
- カレンダーデータに機密情報が含まれる場合は適切なファイルパーミッション設定が必要

## 備考

- calfwは日本語表示に対応しており、曜日・月名の日本語表示が可能
- Evil modeが有効な場合、h/j/k/lでのナビゲーションが可能
- ポップアップルールにより詳細表示は下部40%の領域に表示される

---

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

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

### 推奨読解順序

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

変数定義を理解し、機能の設定オプションを把握する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | autoload.el | `modules/app/calendar/autoload.el` | +calendar--wconf、+calendar-workspace-name変数の定義 |

**読解のコツ**: Emacs Lispの`defvar`はグローバル変数定義、`defun`は関数定義。`;;;###autoload`マジックコメントは自動ロード対象を示す。

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

ユーザーが呼び出すメインコマンドを把握する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | autoload.el | `modules/app/calendar/autoload.el` | =calendar関数（14-30行目） |

**主要処理フロー**:
1. **14行目**: `=calendar`関数定義開始、interactiveコマンド
2. **17行目**: workspacesモジュール有効時は専用ワークスペースに切り替え
3. **20-25行目**: 既存カレンダーバッファの確認と初期化処理の分岐
4. **27行目**: workspaces無効時のウィンドウ設定保存
5. **30行目**: +calendar--init呼び出し

#### Step 3: 初期化処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | autoload.el | `modules/app/calendar/autoload.el` | +calendar--init関数（7-11行目） |
| 3-2 | autoload.el | `modules/app/calendar/autoload.el` | +calendar/open-calendar関数（45-49行目） |

**主要処理フロー**:
- **7-11行目**: calfwのrequireとバッファ存在確認、+calendar-open-function呼び出し
- **45-49行目**: calfw-org-open-calendarを"org-agenda"ソースで呼び出し

#### Step 4: 設定と統合を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | config.el | `modules/app/calendar/config.el` | calfw設定（10-72行目） |
| 4-2 | config.el | `modules/app/calendar/config.el` | calfw-org設定（75-79行目） |
| 4-3 | config.el | `modules/app/calendar/config.el` | org-gcal設定（90-94行目） |

**主要処理フロー**:
- **14-23行目**: calfwの罫線文字設定（Unicode文字使用）
- **25行目**: 詳細ポップアップのルール設定
- **27行目**: qキーで終了するキーバインド
- **28-67行目**: Evil mode有効時のキーバインド設定
- **69行目**: doom-mark-buffer-as-real-hフック追加
- **90-94行目**: org-gcalのディレクトリとトークンファイルパス設定

#### Step 5: 終了処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 5-1 | autoload.el | `modules/app/calendar/autoload.el` | +calendar/quit関数（33-42行目） |

**主要処理フロー**:
- **36-38行目**: workspaces有効時はワークスペースを削除
- **39-41行目**: workspaces無効時はウィンドウ設定を復元
- **42行目**: *cfw[-:]で始まるバッファを削除

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

```
=calendar
    │
    ├─ +workspace-switch (ui/workspaces)
    │      └─ persp-switch
    │
    ├─ doom/switch-to-scratch-buffer
    │
    └─ +calendar--init
           │
           ├─ require 'calfw
           │
           └─ +calendar-open-function
                  │
                  └─ +calendar/open-calendar
                         │
                         └─ calfw-org-open-calendar
                                │
                                ├─ calfw-org-create-source
                                └─ calfw-open-calendar-buffer
```

### データフロー図

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

org-agenda-files ─────────┐
                          │
diary-file ───────────────┼──▶ calfw-open-calendar-buffer ──▶ *calfw-calendar*
                          │          │
iCal URL/file ────────────┤          └──▶ calfw-show-details ──▶ *calfw-details*
                          │
Google Calendar API ──────┘
(via org-gcal)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| config.el | `modules/app/calendar/config.el` | ソース | パッケージ設定とキーバインド定義 |
| autoload.el | `modules/app/calendar/autoload.el` | ソース | 自動ロード関数定義 |
| packages.el | `modules/app/calendar/packages.el` | 設定 | 依存パッケージの宣言 |
