# 機能設計書 144-アバター管理

## 概要

本ドキュメントは、GitLabのアバター管理機能に関する設計書である。アバター管理機能はユーザー、プロジェクト、グループのアバター画像の表示・削除を担う。

### 本機能の処理概要

アバター管理機能は、GitLab上の各エンティティ（ユーザー、プロジェクト、グループ）に関連付けられたアバター画像を管理する。リポジトリに格納されたアバター画像の取得・表示、アバターの削除などの操作を提供する。

**業務上の目的・背景**：ユーザーやプロジェクトを視覚的に識別しやすくするため、アバター画像を設定・管理する機能が必要である。プロジェクトのアバターはリポジトリ内のファイルとしても管理でき、コードと共にバージョン管理される利点がある。

**機能の利用シーン**：
- プロジェクト設定画面でのアバター表示
- プロジェクトのアバター画像の削除
- Gitリポジトリに格納されたアバター画像の取得・表示
- カスタム絵文字の管理（グループレベル）

**主要な処理内容**：
1. リポジトリからアバター画像のBlobを取得
2. アバター画像のストリーム配信
3. アバター画像の削除
4. キャッシュ制御（公開プロジェクトの場合）

**関連システム・外部連携**：
- Gitalyサーバー（リポジトリからのBlob取得）
- CarrierWaveアップローダー（ファイルストレージ）

**権限による制御**：
- 表示（show）: プロジェクトへの読み取り権限
- 削除（destroy）: プロジェクト管理者権限（:admin_project）

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 165 | カスタム絵文字 | 主機能 | カスタム絵文字の管理 |

## 機能種別

ファイル操作 / 画像配信

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| project_id | Integer | Yes | プロジェクトID（URL経由） | 存在するプロジェクトであること |

### 入力データソース

- URLパラメータ（プロジェクトID）
- リポジトリ内のアバターファイル（.avatar形式）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| Blob | Binary | アバター画像のバイナリデータ |
| Content-Type | String | 画像のMIMEタイプ |

### 出力先

- HTTPレスポンス（画像ストリーム）
- リダイレクト（削除後はプロジェクト編集画面へ）

## 処理フロー

### 処理シーケンス

```
1. showアクション（アバター表示）
   └─ リポジトリからroot_refを取得
   └─ avatar_in_gitパスでBlobを取得
   └─ send_blobでストリーム配信
   └─ 公開プロジェクトの場合はキャッシュ許可

2. destroyアクション（アバター削除）
   └─ authorize_admin_project!で権限確認
   └─ project.remove_avatar!
   └─ project.save
   └─ プロジェクト編集画面へリダイレクト
```

### フローチャート

```mermaid
flowchart TD
    A[リクエスト受信] --> B{アクション判定}

    B -->|show| C[リポジトリからBlob取得]
    B -->|destroy| D{管理者権限?}

    C --> E{Blob存在?}
    E -->|Yes| F{公開プロジェクト?}
    E -->|No| G[404エラー]

    F -->|Yes| H[キャッシュ許可して配信]
    F -->|No| I[キャッシュなしで配信]

    D -->|Yes| J[アバター削除]
    D -->|No| K[アクセス拒否]

    J --> L[プロジェクト保存]
    L --> M[編集画面へリダイレクト]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-144-01 | 管理者権限必須 | アバター削除には管理者権限が必要 | destroyアクション |
| BR-144-02 | 公開プロジェクトキャッシュ | 公開プロジェクトのアバターはキャッシュ許可 | project.public? = true |
| BR-144-03 | リポジトリアバター | アバターはリポジトリのroot_refから取得 | showアクション |

### 計算ロジック

特になし

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

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

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| アバター取得 | projects | SELECT | プロジェクト情報取得 |
| アバター削除 | projects | UPDATE | avatar関連カラムのクリア |
| アバター削除 | uploads | DELETE | アップロードファイル情報削除 |

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

#### projects

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | id, avatar, visibility_level | id = params[:project_id] | プロジェクト情報取得 |
| UPDATE | avatar | NULL | アバター削除時 |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| 404 | Not Found | Blobが存在しない | エラーページ表示 |
| 403 | Forbidden | 管理者権限がない（destroy時） | アクセス拒否 |

### リトライ仕様

特になし

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

- destroyアクションはプロジェクト保存時にトランザクション内で実行

## パフォーマンス要件

- urgency: low（低優先度）
- 公開プロジェクトのアバターはキャッシュ活用

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

- 管理者権限チェック（authorize_admin_project!）
- Blob送信時のセキュリティ制御（SendsBlob concern）

## 備考

- feature_category: groups_and_projects
- プロジェクトのアバターはGitリポジトリ内のファイルとしても管理可能
- リダイレクト先のアンカー: #js-general-project-settings

---

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

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

### 推奨読解順序

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

メインコントローラの処理フローを把握する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | avatars_controller.rb | `app/controllers/projects/avatars_controller.rb` | アバター管理のエントリーポイント |

**主要処理フロー**:
1. **4行目**: include SendsBlob - Blob送信機能の取り込み
2. **6行目**: before_action :authorize_admin_project! - 削除時の権限チェック
3. **12-15行目**: show アクション - リポジトリからBlobを取得して配信
4. **17-22行目**: destroy アクション - アバター削除と保存

**読解のコツ**:
- `@repository.blob_at_branch`でGitリポジトリからBlobを取得
- `send_blob`メソッドはSendsBlobモジュールで定義
- `allow_caching`オプションで公開プロジェクトのキャッシュを制御

#### Step 2: Blob送信機能を理解する

SendsBlobモジュールの実装を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | sends_blob.rb | `app/controllers/concerns/sends_blob.rb` | Blob送信処理 |

#### Step 3: プロジェクトモデルのアバター関連を理解する

プロジェクトモデルのアバター関連メソッドを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | project.rb | `app/models/project.rb` | avatar_in_git, remove_avatar! メソッド |

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

```
Projects::AvatarsController
    │
    ├─ show
    │      ├─ @repository.blob_at_branch(@repository.root_ref, @project.avatar_in_git)
    │      │      └─ Gitaly経由でBlobを取得
    │      └─ send_blob(@repository, @blob, allow_caching: @project.public?)
    │             └─ SendsBlob#send_blob
    │
    └─ destroy
           ├─ authorize_admin_project!
           ├─ @project.remove_avatar!
           │      └─ CarrierWave uploader
           ├─ @project.save
           └─ redirect_to edit_project_path
```

### データフロー図

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

GET /avatar           ───▶  AvatarsController#show    ───▶  画像ストリーム
                            ├─ Blob取得（Gitaly）
                            └─ send_blob

DELETE /avatar        ───▶  AvatarsController#destroy ───▶  リダイレクト
                            ├─ remove_avatar!
                            └─ save
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| avatars_controller.rb | `app/controllers/projects/avatars_controller.rb` | コントローラ | アバター管理のエントリーポイント |
| sends_blob.rb | `app/controllers/concerns/sends_blob.rb` | Concern | Blob送信処理 |
| project.rb | `app/models/project.rb` | モデル | プロジェクトモデル（avatar関連メソッド） |
| avatar_uploader.rb | `app/uploaders/avatar_uploader.rb` | アップローダー | アバターアップロード処理 |
