# 画面設計書 114-リージョン作成画面

## 概要

本ドキュメントは、Medusa Admin Dashboardにおけるリージョン作成画面に関する設計書です。この画面により、新しいリージョン（地域設定）を作成することができます。

### 本画面の処理概要

**業務上の目的・背景**：新しい販売対象地域を追加する際に、その地域に固有の設定（通貨、税金、決済プロバイダー、対象国）を定義する必要があります。本画面では、これらの設定を一括で行い、新規リージョンを作成します。

**画面へのアクセス方法**：リージョン一覧画面（/settings/regions）の「作成」ボタンをクリック、またはURL直接アクセス（/settings/regions/create）。

**主要な操作・処理内容**：
1. リージョン名の入力
2. 通貨の選択（ストアでサポートされている通貨から選択）
3. 自動税金計算の有効/無効設定
4. 税込価格の有効/無効設定
5. 対象国の選択（スタックモーダルで選択）
6. 決済プロバイダーの選択
7. リージョンの保存

**画面遷移**：
- 遷移元：リージョン一覧画面（/settings/regions）
- 遷移先：保存成功時はリージョン詳細画面（/settings/regions/:id）、キャンセル時はリージョン一覧画面

**権限による表示制御**：管理者権限を持つユーザーのみがアクセス可能です。

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 65 | 地域CRUD | 主機能 | 新規リージョンの作成 |
| 66 | 地域国設定 | 補助機能 | リージョンに含める国の設定 |

## 画面種別

モーダル形式（RouteFocusModal）の登録画面

## URL/ルーティング

`/settings/regions/create`

## 入出力項目

| 項目名 | 項目ID | 型 | 必須 | 説明 |
|--------|--------|------|------|------|
| リージョン名 | name | string | 必須 | リージョンの名称 |
| 通貨 | currency_code | string | 必須 | 通貨コード（2文字以上） |
| 自動税金計算 | automatic_taxes | boolean | - | 自動税金計算の有効/無効 |
| 税込価格 | is_tax_inclusive | boolean | - | 税込価格の有効/無効 |
| 対象国 | countries | object[] | - | 対象国の配列（code, name） |
| 決済プロバイダー | payment_providers | string[] | 必須（1件以上） | 決済プロバイダーID配列 |

## 表示項目

### 基本情報セクション

| 項目名 | 項目ID | 型 | 説明 |
|--------|--------|------|------|
| リージョン名入力 | name | Input | テキスト入力フィールド |
| 通貨選択 | currency_code | Select | ストアサポート通貨のドロップダウン |

### 税金設定セクション

| 項目名 | 項目ID | 型 | 説明 |
|--------|--------|------|------|
| 自動税金計算 | automatic_taxes | Switch | トグルスイッチ（デフォルト: ON） |
| 税込価格 | is_tax_inclusive | Switch | トグルスイッチ（デフォルト: OFF） |

### 国設定セクション

| 項目名 | 項目ID | 型 | 説明 |
|--------|--------|------|------|
| 選択済み国タグ | - | Tag[] | 選択された国の一覧（タグ形式） |
| 国追加ボタン | - | Button | スタックモーダルを開く |
| 全クリアボタン | - | Button | 選択をすべてクリア |

### 決済プロバイダーセクション

| 項目名 | 項目ID | 型 | 説明 |
|--------|--------|------|------|
| 決済プロバイダー | payment_providers | Combobox | 有効なプロバイダーの複数選択 |

## イベント仕様

### 1-国追加モーダル表示

**トリガー**：「国を追加」ボタンをクリック

**処理内容**：
1. StackedFocusModalを開く
2. 国一覧をテーブル形式で表示
3. チェックボックスで複数選択可能
4. 検索・ソート機能を提供

### 2-国選択確定

**トリガー**：国追加モーダルの「保存」ボタンをクリック

**処理内容**：
1. rowSelectionから選択された国コードを取得
2. countriesフィールドに{code, name}形式で設定
3. モーダルを閉じる

### 3-国タグ削除

**トリガー**：選択済み国タグの×ボタンをクリック

**処理内容**：
1. 該当国をcountriesフィールドから削除
2. rowSelectionからも削除

### 4-全クリア

**トリガー**：「すべてクリア」ボタンをクリック

**処理内容**：
1. countriesフィールドを空配列に設定
2. rowSelectionを空オブジェクトに設定

### 5-保存

**トリガー**：「保存」ボタンをクリック

**処理内容**：
1. フォームバリデーション実行
2. useCreateRegionフックでリージョン作成APIを呼び出し
3. 成功時：トースト通知を表示し、リージョン詳細画面へ遷移
4. 失敗時：エラートースト通知を表示

### 6-キャンセル

**トリガー**：「キャンセル」ボタンをクリック

**処理内容**：
1. モーダルを閉じてリージョン一覧画面に戻る

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

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

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| 保存ボタン押下 | region | INSERT | 新規リージョンの作成 |
| 保存ボタン押下 | region_country | INSERT | リージョンと国の紐付け |
| 保存ボタン押下 | price_preference | INSERT/UPDATE | 税込価格設定 |

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

#### region

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| INSERT | name | フォーム入力値 | リージョン名 |
| INSERT | currency_code | フォーム選択値（小文字） | 通貨コード |
| INSERT | automatic_taxes | フォーム選択値 | 自動税金計算フラグ |
| INSERT | created_at | 現在日時 | 自動設定 |
| INSERT | updated_at | 現在日時 | 自動設定 |

## メッセージ仕様

| メッセージID | 種別 | メッセージ内容 | 表示条件 |
|-------------|------|--------------|---------|
| regions.toast.create | 成功 | リージョンが作成されました | 作成成功時 |
| - | エラー | {エラーメッセージ} | API呼び出し失敗時 |

## 例外処理

| 例外条件 | 処理内容 |
|---------|---------|
| ストア情報取得エラー | エラーをスローしてエラーバウンダリで処理 |
| 作成API失敗 | エラートーストを表示、フォームは維持 |
| バリデーションエラー | 各フィールドにエラーメッセージを表示 |

## 備考

- 通貨はストアでサポートされている通貨のみ選択可能
- 国選択はスタックモーダル形式で、メインフォームと独立して操作
- 決済プロバイダーはComboboxでインクリメンタル検索・ページネーション対応
- 国一覧のページサイズは50件

---

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

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

### 推奨読解順序

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

リージョン作成時のデータ構造を理解します。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | create-region-form.tsx | `packages/admin/dashboard/src/routes/regions/region-create/components/create-region-form/create-region-form.tsx` | CreateRegionSchemaの定義（48-55行目） |

**読解のコツ**: Zodスキーマでname（必須）、currency_code（2文字以上）、payment_providers（1件以上）が必須であることを確認します。

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | region-create.tsx | `packages/admin/dashboard/src/routes/regions/region-create/region-create.tsx` | コンポーネントのエントリーポイント |

**主要処理フロー**:
1. **7行目**: useStoreでストア情報を取得
2. **9-11行目**: ストアの対応通貨を取得
3. **17-21行目**: RouteFocusModalでCreateRegionFormをラップ

#### Step 3: フォームロジックを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | create-region-form.tsx | `packages/admin/dashboard/src/routes/regions/region-create/components/create-region-form/create-region-form.tsx` | メインフォームロジック |

**主要処理フロー**:
- **48-55行目**: Zodバリデーションスキーマ
- **62-77行目**: useFormでフォーム初期化、デフォルト値設定
- **79-83行目**: useWatchで選択済み国を監視
- **87-110行目**: handleSubmit - useCreateRegionでAPI呼び出し
- **112-128行目**: useCountriesで国一覧を取得（静的データをフィルタ）
- **147-161行目**: saveCountries - 国選択確定処理
- **164-175行目**: removeCountry - 個別国削除
- **177-180行目**: clearCountries - 全クリア
- **182-191行目**: useComboboxDataで決済プロバイダー取得

#### Step 4: APIフックを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | regions.tsx | `packages/admin/dashboard/src/hooks/api/regions.tsx` | リージョンAPIフック |

**主要処理フロー**:
- **61-84行目**: useCreateRegion - リージョン作成、成功時にリスト・詳細キャッシュ無効化

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

```
RegionCreate (region-create.tsx)
    │
    ├─ useStore()
    │      └─ sdk.admin.store.list()
    │
    └─ CreateRegionForm
           │
           ├─ useForm() + useWatch()
           │      └─ フォーム状態管理
           │
           ├─ useCountries()
           │      └─ 静的国データのフィルタ
           │
           ├─ StackedFocusModal
           │      └─ 国選択テーブル
           │
           ├─ useComboboxData()
           │      └─ sdk.admin.payment.listPaymentProviders()
           │
           └─ useCreateRegion()
                  └─ sdk.admin.region.create()
```

### データフロー図

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

name入力 ──────────▶ フォーム状態 ────────────────▶
currency選択 ───────▶ フォーム状態 ────────────────▶
automatic_taxes ────▶ フォーム状態 ────────────────▶  保存ボタン
is_tax_inclusive ───▶ フォーム状態 ────────────────▶     │
国選択モーダル ─────▶ rowSelection → countries ───▶     │
プロバイダー選択 ───▶ フォーム状態 ────────────────▶     │
                                                        ▼
                                              useCreateRegion()
                                                        │
                                                        ▼
                                              [Region APIサーバー]
                                                        │
                                                        ▼
                                              詳細画面へ遷移
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| region-create.tsx | `packages/admin/dashboard/src/routes/regions/region-create/region-create.tsx` | ソース | エントリーポイント |
| create-region-form.tsx | `packages/admin/dashboard/src/routes/regions/region-create/components/create-region-form/create-region-form.tsx` | ソース | メインフォームコンポーネント |
| regions.tsx | `packages/admin/dashboard/src/hooks/api/regions.tsx` | ソース | リージョンAPIフック |
| store.tsx | `packages/admin/dashboard/src/hooks/api/store.tsx` | ソース | ストアAPIフック |
| countries.ts | `packages/admin/dashboard/src/lib/data/countries.ts` | データ | 静的国データ |
| currencies.ts | `packages/admin/dashboard/src/lib/data/currencies.ts` | データ | 通貨データ |
| use-combobox-data.tsx | `packages/admin/dashboard/src/hooks/use-combobox-data.tsx` | ソース | コンボボックスデータフック |
| stacked-focus-modal.tsx | `packages/admin/dashboard/src/components/modals/stacked-focus-modal/` | ソース | スタックモーダルコンポーネント |
