# 画面設計書 54-定型文一覧画面

## 概要

本ドキュメントは、Chatwootの定型文一覧画面の設計書です。顧客対応で頻繁に使用するメッセージテンプレート（Canned Response）の作成・編集・削除を管理する画面です。

### 本画面の処理概要

定型文（Canned Response）の一覧表示と管理を行う画面です。エージェントがチャット中に素早く定型メッセージを挿入するために使用されます。

**業務上の目的・背景**：カスタマーサポートでは、挨拶、FAQ回答、クロージングメッセージなど、頻繁に使用するフレーズがあります。定型文機能により、タイピング時間を削減し、一貫性のある高品質な対応を実現します。ショートコード（例：`/hello`）を入力することで素早く定型文を挿入できます。

**画面へのアクセス方法**：設定メニュー > 定型文

**主要な操作・処理内容**：
1. 定型文一覧の表示（ショートコード、内容）
2. ショートコードによるソート（昇順/降順切り替え）
3. 新規定型文作成（モーダル）
4. 定型文編集（モーダル）
5. 定型文削除（確認モーダル）

**画面遷移**：
- 遷移元: 設定ホーム画面
- 遷移先: なし（モーダル操作のみ）

**権限による表示制御**：全ロール（管理者、エージェント）がアクセス可能

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 80 | キャンドレスポンス | 主機能 | 定型文の一覧と管理 |

## 画面種別

一覧

## URL/ルーティング

- パス: `/app/accounts/:accountId/settings/canned-response`
- ルート名: `canned_list`（推定）
- 権限: 全ロール対応

## 入出力項目

なし（一覧表示のみ、操作はモーダルで実行）

## 表示項目

| 項目名 | 型 | 説明 |
|--------|------|------|
| records | Array<CannedResponse> | 定型文一覧（ソート済み） |
| cannedItem.short_code | String | ショートコード |
| cannedItem.content | String | 定型文内容（プレーンテキスト表示） |

### テーブルヘッダー

| カラム名 | キー | 説明 |
|----------|------|------|
| ショートコード | CANNED_MGMT.LIST.TABLE_HEADER.SHORT_CODE | ソート可能 |
| 内容 | CANNED_MGMT.LIST.TABLE_HEADER.CONTENT | 定型文内容 |
| アクション | CANNED_MGMT.LIST.TABLE_HEADER.ACTIONS | 編集・削除ボタン |

## イベント仕様

### 1-ソート切り替え（toggleSort）

**トリガー**: ショートコードヘッダーをクリック

**処理フロー**:
1. `sortOrder`を'asc'と'desc'で切り替え
2. `getSortedCannedResponses`ゲッターがソート順を反映

### 2-定型文追加ボタン押下（openAddPopup）

**トリガー**: 「定型文追加」ボタン押下

**処理フロー**:
1. `showAddPopup`をtrueに設定
2. AddCannedモーダルコンポーネントを表示

### 3-定型文編集ボタン押下（openEditPopup）

**トリガー**: 各定型文行の編集ボタン押下

**処理フロー**:
1. `showEditPopup`をtrueに設定
2. `activeResponse`に対象定型文オブジェクトを格納
3. EditCannedモーダルコンポーネントを表示

### 4-定型文削除ボタン押下（openDeletePopup）

**トリガー**: 各定型文行の削除ボタン押下

**処理フロー**:
1. `showDeleteConfirmationPopup`をtrueに設定
2. `activeResponse`に対象定型文オブジェクトを格納
3. 削除確認モーダルを表示

### 5-削除確認（confirmDeletion）

**トリガー**: 削除確認モーダルで「はい」押下

**処理フロー**:
1. `loading[activeResponse.id]`をtrueに設定
2. モーダルを閉じる
3. `deleteCannedResponse(activeResponse.id)`を呼び出し

### 6-定型文削除（deleteCannedResponse）

**トリガー**: confirmDeletionから呼び出し

**処理フロー**:
1. `store.dispatch('deleteCannedResponse', id)`を実行
2. 成功時: 成功メッセージをアラート表示
3. 失敗時: エラーメッセージをアラート表示

### 7-定型文作成（AddCanned内のaddCannedResponse）

**トリガー**: 追加モーダルで「作成」ボタン押下

**処理フロー**:
1. `store.dispatch('createCannedResponse', {...})`を実行
2. 成功時: 成功メッセージをアラート表示、フォームリセット、モーダルを閉じる
3. 失敗時: エラーメッセージをアラート表示

## データベース更新仕様

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

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| 定型文追加 | canned_responses | INSERT | 新規定型文を作成 |
| 定型文編集 | canned_responses | UPDATE | 既存定型文を更新 |
| 定型文削除 | canned_responses | DELETE | 定型文を削除 |
| 画面表示 | canned_responses | SELECT | 定型文一覧を取得 |

### テーブル別更新項目詳細

#### canned_responses

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| INSERT | short_code | フォーム入力値 | 必須、最低2文字 |
| INSERT | content | リッチテキストエディタの内容 | 必須 |
| UPDATE | short_code | フォーム入力値 | 必須、最低2文字 |
| UPDATE | content | リッチテキストエディタの内容 | 必須 |
| DELETE | id | 対象定型文のID | 物理削除 |

## メッセージ仕様

| 種別 | キー | 表示条件 | メッセージ内容 |
|------|------|----------|--------------|
| 成功 | CANNED_MGMT.ADD.API.SUCCESS_MESSAGE | 定型文作成成功時 | 定型文作成成功 |
| エラー | CANNED_MGMT.ADD.API.ERROR_MESSAGE | 定型文作成失敗時 | 定型文作成エラー |
| 成功 | CANNED_MGMT.EDIT.API.SUCCESS_MESSAGE | 定型文更新成功時 | 定型文更新成功 |
| エラー | CANNED_MGMT.EDIT.API.ERROR_MESSAGE | 定型文更新失敗時 | 定型文更新エラー |
| 成功 | CANNED_MGMT.DELETE.API.SUCCESS_MESSAGE | 定型文削除成功時 | 定型文削除成功 |
| エラー | CANNED_MGMT.DELETE.API.ERROR_MESSAGE | 定型文削除失敗時 | 定型文削除エラー |
| 情報 | CANNED_MGMT.LOADING | 読み込み中 | 読み込み中メッセージ |
| 情報 | CANNED_MGMT.LIST.404 | 定型文なし | 定型文が見つかりません |

## 例外処理

| 例外状況 | 対応処理 |
|----------|----------|
| 定型文一覧が空 | 「定型文が見つかりません」メッセージを表示 |
| API通信エラー | `useAlert()`でエラーメッセージをトースト表示 |
| バリデーションエラー | フォームにエラーメッセージを表示（ショートコード最低2文字など） |
| 読み込み中 | ローディングスピナーを表示 |

## 備考

- 定型文の内容はリッチテキスト形式（WootMessageEditor使用）
- 表示時はプレーンテキストに変換（getPlainText）
- ショートコードは会話画面で`/`に続けて入力することで補完候補に表示
- 定型文内で変数（例：`{{contact.name}}`）を使用可能

---

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

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

### 推奨読解順序

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

定型文のデータ構造とストア管理を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | cannedResponse.js | `app/javascript/dashboard/store/modules/cannedResponse.js` | Vuexストアの構造、CRUD操作 |
| 1-2 | cannedResponse.js | `app/javascript/dashboard/api/cannedResponse.js` | APIクライアント定義 |

**読解のコツ**: グローバルストアとして定義されており、namespaceなしでアクションをディスパッチする。

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

メインコンポーネントの構造を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | Index.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/Index.vue` | 一覧表示、ソート、モーダル制御 |

**主要処理フロー**:
1. **L62-64**: `onMounted`で定型文一覧を取得
2. **L31-33**: `records`でソート済み定型文一覧を取得（`getSortedCannedResponses`）
3. **L50-52**: `toggleSort`でソート順切り替え
4. **L97-106**: `deleteCannedResponse`で削除処理

#### Step 3: モーダルコンポーネントを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | AddCanned.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/AddCanned.vue` | 定型文作成フォーム |
| 3-2 | EditCanned.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/EditCanned.vue` | 定型文編集フォーム |

**主要処理フロー**:
- **AddCanned L57-79**: `addCannedResponse()`で新規作成
- リッチテキストエディタ（WootMessageEditor）を使用

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

```
Index.vue (コンポーネント)
    │
    ├─ onMounted()
    │      └─ fetchCannedResponses()
    │             └─ store.dispatch('getCannedResponse')
    │                    └─ CannedResponseAPI.get()
    │
    ├─ toggleSort()
    │      └─ sortOrder = 'asc' | 'desc'
    │             └─ getSortedCannedResponses(sortOrder)
    │
    ├─ openAddPopup()
    │      └─ AddCanned.vue (モーダル)
    │             └─ addCannedResponse()
    │                    └─ store.dispatch('createCannedResponse', {...})
    │
    ├─ openEditPopup(item)
    │      └─ EditCanned.vue (モーダル)
    │             └─ updateCannedResponse()
    │                    └─ store.dispatch('updateCannedResponse', {...})
    │
    └─ openDeletePopup(item)
           └─ woot-delete-modal
                  └─ confirmDeletion()
                         └─ deleteCannedResponse(id)
                                └─ store.dispatch('deleteCannedResponse', id)
```

### データフロー図

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

                    ┌──▶ store.dispatch('getCannedResponse')
onMounted() ────────┤         │
                    │         ▼
                    │    CannedResponseAPI.get() ──────▶ records (Vuex Store)
                    │                                         │
                    └──▶ getSortedCannedResponses(order) ◀───┘
                                │
                                ▼
                          records (computed)
                                │
                        getPlainText()
                                │
                                ▼
                          テーブル表示

[ソート]
sortOrder ('asc'/'desc') ──▶ getSortedCannedResponses ──▶ ソート済みリスト

[CRUD操作]
                    ┌──▶ createCannedResponse ──▶ ADD_CANNED
ユーザー操作 ───────┼──▶ updateCannedResponse ──▶ EDIT_CANNED
                    └──▶ deleteCannedResponse ──▶ DELETE_CANNED
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| Index.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/Index.vue` | ソース | メインコンポーネント |
| AddCanned.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/AddCanned.vue` | ソース | 追加モーダル |
| EditCanned.vue | `app/javascript/dashboard/routes/dashboard/settings/canned/EditCanned.vue` | ソース | 編集モーダル |
| cannedResponse.js | `app/javascript/dashboard/store/modules/cannedResponse.js` | ソース | Vuexストア |
| cannedResponse.js | `app/javascript/dashboard/api/cannedResponse.js` | ソース | APIクライアント |
| WootMessageEditor.vue | `app/javascript/dashboard/components/widgets/WootWriter/Editor.vue` | ソース | リッチテキストエディタ |
| BaseSettingsHeader.vue | `app/javascript/dashboard/routes/dashboard/settings/components/BaseSettingsHeader.vue` | ソース | ヘッダーコンポーネント |
| useMessageFormatter.js | `app/javascript/shared/composables/useMessageFormatter.js` | ソース | テキスト変換ユーティリティ |
