# 機能設計書 69-タグ管理一覧

## 概要

本ドキュメントは、Fat Free CRM の管理機能における「タグ管理一覧」機能の設計を記述する。

### 本機能の処理概要

管理者がシステムに登録されている全タグを一覧表示するための機能である。タグとは、各エンティティ（取引先、連絡先、リード、商談等）に付与できるラベルであり、分類やフィルタリングに使用される。

**業務上の目的・背景**：CRM システムでは、顧客や案件を様々な観点で分類・整理する必要がある。タグ機能により、標準的なカテゴリ分類に加えて、ユーザー独自の分類を柔軟に行うことが可能となる。本機能は、システム全体のタグを管理・整理するための管理者向け機能である。

**機能の利用シーン**：
- システム内のタグ一覧の確認
- タグの使用状況（何件のエンティティに紐付いているか）の確認
- タグの整理・統合作業の準備
- フィールドグループとの関連確認

**主要な処理内容**：
1. 全タグレコードの取得
2. 各タグの使用状況（taggings_count）の表示
3. 各タグとフィールドグループの関連表示
4. 編集・削除リンクの表示

**関連システム・外部連携**：acts-as-taggable-on gem を使用したタグ機能を利用。

**権限による制御**：本機能は管理者権限（admin: true）を持つユーザーのみがアクセス可能。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 42 | タグ管理画面 | 主画面 | 全タグ一覧表示（管理者用） |

## 機能種別

CRUD操作（Read）/ 一覧表示

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| - | - | - | - | - |

### 入力データソース

- なし（全タグを取得）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| @tags | ActiveRecord::Relation | タグの一覧 |

### 出力先

- 画面表示（HTML）

## 処理フロー

### 処理シーケンス

```
1. 管理者がタグ管理一覧画面にアクセス
   └─ GET /admin/tags

2. index アクションでタグ一覧を取得
   └─ Tag.all で全タグを取得

3. 一覧画面を表示
   └─ 各タグの名前と使用状況を表示
   └─ フィールドグループとの関連を表示
   └─ 編集・削除リンクを表示
```

### フローチャート

```mermaid
flowchart TD
    A[タグ管理一覧アクセス] --> B[GET /admin/tags]
    B --> C[Tag.all で全タグ取得]
    C --> D[index.html.haml レンダリング]
    D --> E{タグ存在?}
    E -->|Yes| F[_tag パーシャルでループ表示]
    E -->|No| G[empty パーシャル表示]
    F --> H[各タグの使用状況を表示]
    H --> I[フィールドグループ関連を表示]
    I --> J[終了]
    G --> J
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-69-01 | 全タグ表示 | システム内の全タグを表示 | 常時 |
| BR-69-02 | 使用状況表示 | タグに紐付いている各エンティティの件数を表示 | taggings が存在する場合 |
| BR-69-03 | フィールドグループ関連 | タグに関連付けられたフィールドグループがある場合、削除不可 | FieldGroup.where(tag_id: tag.id).any? |

### 計算ロジック

**model_tagging_counts メソッド（Tag モデル）**：
```ruby
def model_tagging_counts
  Tagging.where(tag_id: id).group(:taggable_type).count
end
```

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

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

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| タグ取得 | tags | SELECT | 全タグレコードの取得 |
| 使用状況取得 | taggings | SELECT | 各タグの使用状況を取得 |
| フィールドグループ取得 | field_groups | SELECT | タグに関連するフィールドグループを取得 |

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

#### tags

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | id, name, taggings_count | なし（全件） | acts-as-taggable-on により管理 |

#### taggings

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | taggable_type, count | tag_id = 対象タグID | GROUP BY taggable_type |

#### field_groups

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | id, label, klass_name | tag_id = 対象タグID | タグに紐付くフィールドグループを取得 |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| - | 認可エラー | 非管理者によるアクセス | ルート画面にリダイレクト |

### リトライ仕様

特になし

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

読み取り専用処理のため、トランザクション管理は不要。

## パフォーマンス要件

- 初期表示のレスポンス時間は 1000ms 以内を目標
- タグ数が多い場合でもページネーションなしで全件表示

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

- 管理者権限チェック（before_action :require_admin_user）
- CSRF トークンによるクロスサイトリクエストフォージェリ対策

## 備考

- タグ一覧から直接編集・削除が可能
- フィールドグループに関連付けられているタグは削除不可（グレーアウト表示）
- 新規タグ作成は「Create Tag」リンクから行う
- AI プロンプトリンク（ai_prompt_link）がある場合、AI によるタグ提案機能が利用可能

---

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

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

### 推奨読解順序

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

まず、タグモデルと taggings、field_groups との関連を理解することが重要。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | tag.rb | `app/models/polymorphic/tag.rb` | タグモデルの定義、model_tagging_counts メソッド |
| 1-2 | schema.rb | `db/schema.rb` | tags テーブル、taggings テーブル、field_groups テーブルの構造 |

**読解のコツ**:
- **8行目**: `class Tag < ActsAsTaggableOn::Tag` で acts-as-taggable-on を継承
- **9行目**: `before_destroy :no_associated_field_groups` でフィールドグループ関連の削除制限
- **18-20行目**: `model_tagging_counts` で各エンティティタイプごとのタグ使用件数を取得

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | tags_controller.rb | `app/controllers/admin/tags_controller.rb` | index アクション |
| 2-2 | application_controller.rb | `app/controllers/admin/application_controller.rb` | 管理者権限チェック |

**主要処理フロー**:
- **16-19行目**: index アクション

```ruby
def index
  @tags = Tag.all
  respond_with(@tags)
end
```

#### Step 3: ビュー層を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | index.html.haml | `app/views/admin/tags/index.html.haml` | タグ一覧画面の構造 |
| 3-2 | _tag.html.haml | `app/views/admin/tags/_tag.html.haml` | タグ行の表示 |

**読解のコツ**:
- `index.html.haml` の4行目で新規作成リンク（link_to_inline）を表示
- `_tag.html.haml` の1-2行目で FieldGroup とのタグ使用状況を取得
- `_tag.html.haml` の7-13行目でフィールドグループ関連がある場合は削除リンクを無効化

#### Step 4: ルーティングを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | routes.rb | `config/routes.rb` | admin/tags のルート定義 |

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

```
[Admin::TagsController#index]
    │
    ├─ load_resource (CanCanCan)
    │
    ├─ @tags = Tag.all
    │
    └─ respond_with(@tags)
           └─ index.html.haml
                  ├─ link_to_inline(:create_tag)
                  │      └─ 新規作成リンク
                  │
                  ├─ @tags.any?
                  │      └─ _tag.html.haml (コレクション)
                  │             ├─ tag_field_groups = FieldGroup.where(tag_id: tag.id)
                  │             ├─ model_tagging_counts = tag.model_tagging_counts
                  │             ├─ link_to_edit(tag)
                  │             ├─ link_to_confirm/link_to_delete（条件分岐）
                  │             └─ フィールドグループ表示
                  │
                  └─ ai_prompt_link（設定がある場合）
```

### データフロー図

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

なし              ───▶ Tag.all                    ───▶ @tags
                           │
                   ───▶ 各タグに対して
                         │
                         ├─ FieldGroup.where(tag_id: id)
                         │      └─ フィールドグループ関連取得
                         │
                         └─ model_tagging_counts
                                └─ taggable_type 別カウント
                                       │
                                       ▼
                                 一覧画面表示
                                 (タグ名、使用状況、関連)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| tags_controller.rb | `app/controllers/admin/tags_controller.rb` | コントローラー | index アクションの実装 |
| application_controller.rb | `app/controllers/admin/application_controller.rb` | コントローラー | 管理者権限チェック |
| tag.rb | `app/models/polymorphic/tag.rb` | モデル | タグモデル定義 |
| index.html.haml | `app/views/admin/tags/index.html.haml` | ビュー | タグ一覧画面 |
| _tag.html.haml | `app/views/admin/tags/_tag.html.haml` | ビュー | タグ行パーシャル |
| routes.rb | `config/routes.rb` | 設定 | ルーティング定義 |
| schema.rb | `db/schema.rb` | 設定 | データベーススキーマ |
