カスタムプラン一覧

概要説明

カスタムプラン一覧機能により、管理者はページネーション付きでカスタムプランを表示、検索、フィルタリングできます。このエンドポイントは複数のフィルタ条件をサポートし、関連データを含むページネーション結果を返します。

前提条件

  • ユーザーは管理者として認証されている必要があります(SuperAdminまたはAdminStaffロール)

依存関係

  • なし(読み取り専用操作)

Swaggerリンク

API: カスタムプラン一覧

ケースドキュメント

ケース1: 契約一覧取得成功

説明

管理者がオプションのフィルタを適用したカスタムプランのページネーション一覧を正常に取得します。結果には関連するサブスクリプション、グループ、ユーザー、パッケージプランのデータが含まれます。

Sequence Diagram

sequenceDiagram
    participant Admin
    participant Controller as CustomContractController
    participant Request as ListCustomContractRequest
    participant Service as CustomContractService
    participant Repository as CustomContractRepository
    participant Database
    
    Note over Admin,Database: GET /api/v1/admin/custom-contracts
    
    rect rgb(200, 255, 200)
    Note right of Admin: Happy Case Flow
    
    Admin->>Controller: GET request with filters
    
    rect rgb(200, 230, 255)
    Note right of Controller: Request Validation
    Controller->>Request: validate(params)
    Request->>Request: Validate filter parameters
    Request->>Request: Validate pagination params
    Request-->>Controller: Validation passed
    end
    
    rect rgb(200, 255, 255)
    Note right of Controller: Query Processing
    Controller->>Service: list(validatedParams)
    Service->>Repository: getQuery() with filters
    Repository->>Repository: Build query with joins
    Repository->>Repository: Apply status filter
    Repository->>Repository: Apply group_name filter
    Repository->>Repository: Apply other filters
    Repository->>Database: Execute paginated query
    Database-->>Repository: Return contract records
    Repository-->>Service: Return paginated collection
    Service-->>Controller: Return paginated results
    end
    
    Controller-->>Admin: 200 OK (contracts, meta, links)
    end

ステップ

ステップ1: リクエスト検証

  • 説明: フィルタとページネーションパラメータを検証します
  • リクエスト: GET /api/v1/admin/custom-contracts?status=offered&group_name=test&page=1&per_page=10
  • 認証: ユーザーはSuperAdminまたはAdminStaffロールを持つ必要があります
  • 利用可能なフィルタ:
    • status: Filter by contract status (offered, active, draft, expired, cancelled, or 'all')
    • group_id: Filter by specific group ID
    • group_name: Filter by group name (partial match, case-insensitive)
    • subscription_id: Filter by subscription ID
    • user_id: Filter by user ID
    • code: Filter by contract code (partial match)
    • per_page: Items per page (default: 10)
    • page: Page number (default: 1)

Step 2: Query Building

  • Description: Build database query with filters and eager loading
  • Action:
    • Load relationships: subscription, group, user, packagePlan
    • Apply status filter (if provided and not 'all')
    • Apply group_id filter (if provided)
    • Apply group_name filter with LIKE query (if provided)
    • Apply subscription_id filter (if provided)
    • Apply user_id filter (if provided)
    • Apply code filter with LIKE query (if provided)
    • Order by id DESC (latest first)
  • Database Operations:
    • SELECT from custom_contracts with LEFT JOINs
    • WHERE clauses for filters
    • ORDER BY id DESC
    • LIMIT and OFFSET for pagination

Step 3: Execute Paginated Query

  • Description: Execute query and return paginated results
  • Action:
    • Execute query with pagination
    • Calculate total count
    • Build pagination meta data
    • Build pagination links (first, last, prev, next)
  • Response Structure:
    • data: Array of contract resources
    • meta: Pagination metadata (total, per_page, current_page, last_page)
    • links: Pagination links (first, last, prev, next)

Database Related Tables & Fields

erDiagram
    custom_contracts {
        bigint id PK
        bigint subscription_id FK
        bigint package_plan_id FK
        bigint group_id FK
        bigint user_id FK
        string code
        string billing_interval
        string currency
        integer amount
        string status
        timestamp created_at
        timestamp updated_at
    }
    subscriptions {
        bigint id PK
        string slug
        bigint package_plan_id FK
        bigint group_id FK
        string status
        timestamp created_at
    }
    groups {
        bigint id PK
        string name
        integer status
        timestamp created_at
    }
    users {
        bigint id PK
        string name
        string email
        timestamp created_at
    }
    package_plans {
        bigint id PK
        string name
        string billing_interval
        timestamp created_at
    }
    
    custom_contracts ||--o| subscriptions : has
    custom_contracts ||--|| groups : belongs_to
    custom_contracts ||--o| users : managed_by
    custom_contracts ||--o| package_plans : based_on

Error Handling

  • Log: Errors are logged via logThrow() method
  • Error Detail:
Status Code Error Message Description
422 Validation error messages When filter parameters are invalid
400 Generic error with exception message For unexpected database errors

Additional Notes

Filter Behavior
  • Status Filter:
    • Accepts single status or comma-separated list
    • 'all' shows contracts in any status
    • Default: shows all statuses
  • Group Name Filter:
    • Case-insensitive partial match
    • Uses SQL LIKE with wildcards: %search%
  • Code Filter:
    • Partial match for contract codes
    • Useful for searching by contract identifier patterns
Pagination
  • Default per_page: 10
  • Minimum per_page: 1
  • Maximum per_page: 100
  • Results always ordered by ID DESC (newest first)
Performance Considerations
  • Indexed fields: status, subscription_id
  • Eager loading prevents N+1 queries
  • Group name filter uses LIKE (consider full-text search for large datasets)
  • Consider caching for frequently accessed pages
Response Format
{
  "status": true,
  "message": "カスタムプラン一覧の取得に成功しました",
  "data": [
    {
      "id": 1,
      "code": "CUSTOM-2026-001",
      "status": "offered",
      "amount": 150000,
      "billing_interval": "month",
      "currency": "jpy",
      "group": {
        "id": 5,
        "name": "Test Corporation"
      },
      "subscription": {
        "id": 10,
        "slug": "sub_abc123"
      },
      "created_at": "2026-02-01T10:30:00Z"
    }
  ],
  "meta": {
    "current_page": 1,
    "last_page": 5,
    "per_page": 10,
    "total": 45
  },
  "links": {
    "first": "http://api.example.com/api/v1/admin/custom-contracts?page=1",
    "last": "http://api.example.com/api/v1/admin/custom-contracts?page=5",
    "prev": null,
    "next": "http://api.example.com/api/v1/admin/custom-contracts?page=2"
  }
}