mcpField
A
api-design

api-design

github.com/mgd34msu開発654 回インストール10 週間前に更新
リポジトリ

api-design について

api-designは、REST、GraphQL、tRPCなどのHTTPエンドポイントを設計・実装する開発者向けスキルです。既存の規約の調査から入力検証、API文書化、型の同期、契約チェックまでを扱います。

主な機能

  1. 01既存ルートと規約を把握
  2. 02入力検証とエラーレスポンスを設計
  3. 03REST・GraphQL・tRPCのエンドポイントを実装
  4. 04OpenAPI文書を生成
  5. 05フロントエンドとバックエンドの型を同期
  6. 06API契約を検証

活用シーン

  1. 01APIエンドポイントやルートを作成
  2. 02リクエスト検証やミドルウェアを追加
  3. 03API文書を生成
  4. 04RESTからtRPCなどへ移行

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/mgd34msu/goodvibes-plugin --skill api-design

インストール後、Claude Code で/api-designを入力して読み込まれたか確認します。

同梱ファイルreferences/api-style-guide.mdscripts/api-checklist.sh

詳細

リソース

scripts/
  api-checklist.sh
references/
  api-style-guide.md

API 設計

このスキルでは、GoodVibes の精度とプロジェクトエンジンツールを使用して、API エンドポイントを設計し実装する方法を説明します。REST API、GraphQL リゾルバー、tRPC プロシージャ、またはあらゆる HTTP エンドポイントを構築する際に、このワークフローを使用してください。

このスキルを使用するタイミング

以下の場合にこのスキルを読み込んでください。

  • 新しい API エンドポイントまたはルートを構築するとき
  • リクエストの検証またはミドルウェアを実装するとき
  • エラーレスポンス形式を設計するとき
  • API ドキュメントを生成するとき
  • フロントエンドとバックエンドの型を同期するとき
  • API パラダイム間(REST から tRPC など)を移行するとき

トリガーフレーズ:「create an API」、「build endpoint」、「implement route」、「add validation」、「GraphQL resolver」、「tRPC procedure」。

コアワークフロー

フェーズ 1:調査

実装を始める前に、既存のパターンを把握してください。

ステップ 1.1:既存のルートを把握する

get_api_routes を使用して、プロジェクト内のすべての API エンドポイントを確認します。

mcp__plugin_goodvibes_project-engine__get_api_routes:
  project_root: "."  # or specific path

確認できる内容:

  • ルートファイルの場所と命名規則
  • 使用中の HTTP メソッド(GET、POST、PUT、DELETE、PATCH)
  • ルート構造(フラットかネストか)
  • フレームワークのパターン(Next.js App Router、Express、Fastify、tRPC)
ステップ 1.2:パターンを見つける

discover を使用して、ミドルウェア、検証、エラー処理、認証のパターンを見つけます。

discover:
  queries:
    - id: middleware
      type: grep
      pattern: "(middleware|use\\()"
      glob: "**/*.{ts,js}"
    - id: validation
      type: grep
      pattern: "(z\\.|yup\\.|joi\\.|validator\\.)"
      glob: "**/*.{ts,js}"
    - id: error_handlers
      type: grep
      pattern: "(catch|try|Error|throw)"
      glob: "src/api/**/*.{ts,js}"
    - id: auth_patterns
      type: grep
      pattern: "(auth|jwt|session|bearer|getServerSession)"
      glob: "**/*.{ts,js}"
  verbosity: files_only

確認できる内容:

  • 使用中の検証ライブラリ(Zod、Yup、Joi)
  • エラー処理のパターン
  • 認証ミドルウェア
  • 既存のルート構造
ステップ 1.3:主要なファイルを読む

代表的なルートファイルを 2~3 個読み、実装パターンを把握します。

precision_read:
  files:
    - path: "src/api/users/route.ts"  # or discovered route
      extract: content
    - path: "src/lib/validation.ts"  # or discovered validation file
      extract: outline
  verbosity: standard
フェーズ 2:意思決定

ニーズに合った API パラダイムを選択します。詳しい判断ツリーについては、references/api-style-guide.md を参照してください。

クイック判断ガイド

REST、GraphQL、tRPC、Server Actions の判断ツリーについては、references/api-style-guide.md を確認してください。

フェーズ 3:実装
ステップ 3.1:検証スキーマを定義する

プロジェクトの検証ライブラリを使用して、リクエストの検証を作成します。

Zod を使用した例:

import { z } from 'zod';

export const createUserSchema = z.object({
  email: z.string().email(),
  name: z.string().min(2).max(100),
  role: z.enum(['user', 'admin']).default('user'),
});

export type CreateUserInput = z.infer<typeof createUserSchema>;

ベストプラクティス:

  • すべての入力(body、query params、headers)を検証する
  • 厳格なスキーマを使用する(未知のキーを許可しない)
  • 明確なエラーメッセージを提示する
  • 再利用できるよう、推論された型をエクスポートする
ステップ 3.2:ルートハンドラーを実装する

プロジェクトの規約に従って、ルートハンドラーを記述します。

Next.js App Router の例:

import { NextRequest, NextResponse } from 'next/server';
import { createUserSchema } from './schema';
import { db } from '@/lib/db';
import { getServerSession } from '@/lib/auth';

export async function POST(request: NextRequest) {
  // 1. Authentication
  const session = await getServerSession();
  if (!session) {
    return NextResponse.json(
      { error: 'Unauthorized' },
      { status: 401 }
    );
  }

  // 2. Parse and validate input
  const body = await request.json();
  const result = createUserSchema.safeParse(body);

  if (!result.success) {
    return NextResponse.json(
      { error: 'Validation failed', details: result.error.flatten() },
      { status: 400 }
    );
  }

  // 3. Authorization check
  if (session.user.role !== 'admin') {
    return NextResponse.json(
      { error: 'Forbidden' },
      { status: 403 }
    );
  }

  // 4. Business logic
  try {
    const user = await db.user.create({
      data: result.data,
    });

    return NextResponse.json(user, { status: 201 });
  } catch (error) {
    console.error('Failed to create user:', error);
    return NextResponse.json(
      { error: 'Internal server error' },
      { status: 500 }
    );
  }
}

tRPC の例:

import { z } from 'zod';
import { protectedProcedure, router } from '../trpc';

export const userRouter = router({
  create: protectedProcedure
    .input(
      z.object({
        email: z.string().email(),
        name: z.string().min(2).max(100),
      })
    )
    .mutation(async ({ ctx, input }) => {
      if (ctx.session.user.role !== 'admin') {
        throw new TRPCError({ code: 'FORBIDDEN' });
      }

      return await ctx.db.user.create({
        data: input,
      });
    }),
});
ステップ 3.3:精度ツールを使用して記述する

precision_write を使用して、ルートファイル、検証スキーマ、型を作成します。

precision_write:
  files:
    - path: "src/app/api/users/route.ts"
      content: |
        import { NextRequest, NextResponse } from 'next/server';
        // ... [full handler implementation]
    - path: "src/app/api/users/schema.ts"
      content: |
        import { z } from 'zod';
        export const createUserSchema = z.object({ ... });
  verbosity: count_only
フェーズ 4:エラー処理
標準エラーレスポンス形式

すべてのエンドポイントで一貫したエラーレスポンスを維持します。

interface APIError {
  error: string;           // Human-readable message
  code?: string;           // Machine-readable error code
  details?: unknown;       // Validation errors or additional context
  trace_id?: string;       // For debugging in production
}

HTTP ステータスコードのガイドライン:

  • 200 - 成功
  • 201 - 作成済み(POST)
  • 204 - コンテンツなし(DELETE)
  • 400 - 不正なリクエスト(検証エラー)
  • 401 - 認証されていない(未認証)
  • 403 - 禁止(権限なし)
  • 404 - 見つからない
  • 409 - 競合(リソースが重複)
  • 500 - 内部サーバーエラー
エラー処理パターン
try {
  // Business logic
} catch (error) {
  // Log for debugging (never expose to client)
  console.error('Operation failed:', error);

  // User-facing error
  return NextResponse.json(
    { error: 'Failed to process request' },
    { status: 500 }
  );
}

決して公開しないもの:

  • 本番環境でのスタックトレース
  • データベースのエラーメッセージ
  • ファイルパスまたは内部構造
  • シークレットまたは認証情報
フェーズ 5:ドキュメント作成
ステップ 5.1:OpenAPI 仕様を生成する

REST API の場合は、OpenAPI ドキュメントを自動生成します。

mcp__plugin_goodvibes_project-engine__generate_openapi:
  project_root: "."
  output_path: "docs/openapi.yaml"

生成される内容:

  • ルートパスと HTTP メソッド
  • リクエスト/レスポンスのスキーマ
  • 認証要件
  • リクエスト/レスポンスの例

ツールが存在しない場合、または失敗した場合は、エンドポイントを手動でドキュメント化します。

# In a routes.md file
POST /api/users
Description: Create a new user
Auth: Required (admin)
Body: { email: string, name: string, role?: 'user' | 'admin' }
Response 201: User object
Response 400: Validation error
Response 401: Unauthorized
Response 403: Forbidden
ステップ 5.2:JSDoc コメントを追加する

JSDoc を使用してルートハンドラーをドキュメント化します。

/**
 * Create a new user.
 * 
 * @requires Authentication (admin role)
 * @body {CreateUserInput} User data
 * @returns {User} Created user object
 * @throws {401} Unauthorized - Not authenticated
 * @throws {403} Forbidden - Not an admin
 * @throws {400} Bad Request - Validation failed
 */
export async function POST(request: NextRequest) {
  // ...
}
フェーズ 6:型安全性
ステップ 6.1:フロントエンド/バックエンドの型を同期する

sync_api_types を使用して、型の整合性を確認します。

mcp__plugin_goodvibes_project-engine__sync_api_types:
  backend_dir: "src/app/api"
  frontend_dir: "src/lib/api-client"

確認される内容:

  • フロントエンドとバックエンドのリクエスト型が一致している
  • レスポンス型に一貫性がある
  • フィールド名や型に不一致がない
  • すべてのエンドポイントに対応するクライアントコードがある
ステップ 6.2:API 型をエクスポートする

クライアントで使用できるように型を公開します。

// src/types/api.ts
export type { CreateUserInput, User } from '@/app/api/users/schema';

tRPC では、型が自動的に推論されます。

// Client code
import { trpc } from '@/lib/trpc';

const user = await trpc.user.create.mutate({
  email: '[email protected]',
  name: 'Test User',
}); // Fully typed!
フェーズ 7:検証
Step 7.1: API コントラクトを検証する

validate_api_contract を使用して、レスポンスが仕様に一致することを確認します。

mcp__plugin_goodvibes_analysis-engine__validate_api_contract:
  spec_path: "docs/openapi.yaml"
  implementation_dir: "src/app/api"

検証内容:

  • レスポンスのスキーマが OpenAPI 仕様に一致していること
  • ステータスコードが正しいこと
  • 必須フィールドが含まれていること
  • 型が正確であること

ツールが存在しない場合は、手動でテストします。

# Use curl or httpie to test endpoints
curl -X POST http://localhost:3000/api/users \
  -H "Content-Type: application/json" \
  -d '{"email":"[email protected]","name":"Test"}'
Step 7.2: 型チェックを実行する

TypeScript のコンパイルを確認します。

precision_exec:
  commands:
    - cmd: "npm run typecheck"
      expect:
        exit_code: 0
        stderr_empty: true
  verbosity: minimal
Step 7.3: API チェックリストスクリプトを実行する

検証スクリプトを使用して、品質を確認します。

bash scripts/api-checklist.sh .

検証スイートの全容については、scripts/api-checklist.sh を参照してください。

ミドルウェアのパターン

references/api-style-guide.md のパターンに従って、認証、CORS、レート制限のミドルウェアを実装します。CORS のオリジンなど、セキュリティ上重要な設定には、必ず環境変数を使用してください。

テスト

成功ケース、バリデーションエラー、認証失敗を網羅する、意味のあるアサーションを用いて API エンドポイントをテストします。テストのパターンについては、references/api-style-guide.md を参照してください。

よくあるアンチパターン

避けること:

  • クライアントからの入力を検証せずに信頼する
  • データベースのエラーをクライアントに公開する
  • 変更処理に GET を使用する
  • エンドポイントごとに異なるレスポンス形式を返す
  • 認証チェックを省略する
  • 認可(リソースの所有権)を無視する
  • ルートハンドラーで any 型を使用する
  • 機密情報(API キー、シークレット)をハードコードする
  • エラーに対して 200 を返す

実施すること:

  • 厳密なスキーマですべての入力を検証する
  • 一貫したエラーレスポンス形式を使用する
  • HTTP のセマンティクスに従う(GET = 読み取り、POST = 作成など)
  • 適切な認証と認可を実装する
  • すべての API コードで TypeScript を使用する
  • 環境変数からシークレットを読み込む
  • 適切なステータスコードを返す
  • デバッグ用にエラーをログに記録する(公開はしない)

クイックリファレンス

調査フェーズ:

get_api_routes: { project_root: "." }
discover: { queries: [middleware, validation, auth], verbosity: files_only }
precision_read: { files: [route examples], extract: content }

実装フェーズ:

precision_write: { files: [route, schema, types], verbosity: count_only }

検証フェーズ:

generate_openapi: { project_root: ".", output_path: "docs/openapi.yaml" }
validate_api_contract: { spec_path: "docs/openapi.yaml" }
sync_api_types: { backend_dir: "src/api", frontend_dir: "src/lib" }
precision_exec: { commands: [{ cmd: "npm run typecheck" }] }

実装後:

bash scripts/api-checklist.sh .

詳細な判断ツリーとフレームワーク固有のパターンについては、references/api-style-guide.md を参照してください。

コメント