FastAPIで作るREST API入門:Pythonで高速なAPI開発を始めよう

FastAPIで作るREST API入門:Pythonで高速なAPI開発を始めよう | mohablog

FastAPIは、Pythonで高速で現代的なREST APIを構築するためのフレームワークです。本記事では、FastAPIの基礎から実装まで、初心者でもわかりやすく解説します。Djangoなどの重いフレームワークではなく、シンプルで高性能なAPI開発を始めたい方は必見です。

目次

FastAPIとは

FastAPIは、Starlette(ウェブフレームワーク)とPydantic(データ検証ライブラリ)をベースにした、2018年に登場した比較的新しいフレームワークです。以下のような特徴があります:

  • 高速:Node.jsやGoと同等のパフォーマンスを実現
  • 簡単:シンプルで直感的な記法で素早く開発可能
  • 自動ドキュメント生成:SwaggerUIやReDocで自動的にAPI仕様書を作成
  • 型ヒント対応:Python 3.6+の型注釈を活用した安全なコード
  • 非同期対応:async/awaitでスケーラブルなAPI構築

環境構築と基本インストール

まず、FastAPIをインストールしましょう。pipコマンドで簡単にセットアップできます:

pip install fastapi uvicorn

uvicornはASGIサーバーで、FastAPIアプリケーションを実行するために必要です。その他の推奨パッケージもインストールしておくと良いでしょう:

pip install python-multipart pydantic

最初のFastAPIアプリケーション

では、シンプルなREST APIを作成してみましょう。以下は「Hello World」レベルのサンプルコードです:

from fastapi import FastAPI

app = FastAPI()

@app.get("/")
async def root():
    return {"message": "Hello, FastAPI!"}

@app.get("/items/{item_id}")
async def read_item(item_id: int, q: str = None):
    return {"item_id": item_id, "q": q}

このコードをmain.pyという名前で保存し、以下のコマンドで実行します:

uvicorn main:app --reload

ブラウザでhttp://127.0.0.1:8000にアクセスすると、APIが動作しているのを確認できます。--reloadオプションを付けると、ファイル変更時に自動的に再起動されるため、開発効率が向上します。

リクエストボディとPydanticモデル

実践的なAPIには、クライアントからのリクエストボディの処理が欠かせません。FastAPIではPydanticを使ってデータ検証を行います:

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()

class Item(BaseModel):
    name: str
    price: float
    description: str = None
    tax: float = None

@app.post("/items/")
async def create_item(item: Item):
    return item

@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item):
    return {"item_id": item_id, "item": item}

ItemというPydanticモデルを定義することで、自動的に以下の処理が実行されます:

  • リクエストボディのJSON形式をItemインスタンスに変換
  • 型チェック(例:priceは必ずfloat型)
  • 必須項目と任意項目の区別(=Noneで任意になる)
  • 自動的にSwaggerドキュメントに反映

自動ドキュメント生成

FastAPIの最大の特徴の一つが、自動的にAPI仕様書を生成する機能です。アプリケーション実行中に以下のURLにアクセスしましょう:

  • http://127.0.0.1:8000/docs – Swagger UIでインタラクティブなドキュメント
  • http://127.0.0.1:8000/redoc – ReDocで読みやすいドキュメント

これらのドキュメントは、コード内の型注釈とdocstringから自動生成されます。追加の設定を記述する必要がなく、コード自体がドキュメントになるというのは、開発効率を大きく向上させます。

クエリパラメータとパスパラメータ

REST APIでは、URLからのデータ取得パターンが複数あります。それぞれを実装してみましょう:

from fastapi import FastAPI
from typing import Optional

app = FastAPI()

# パスパラメータ
@app.get("/users/{user_id}")
async def get_user(user_id: int):
    return {"user_id": user_id}

# クエリパラメータ
@app.get("/search/")
async def search(q: str, skip: int = 0, limit: int = 10):
    return {"query": q, "skip": skip, "limit": limit}

# 複合パラメータ
@app.get("/products/{category}/")
async def get_products(category: str, skip: int = 0, limit: int = 20, on_sale: Optional[bool] = None):
    return {
        "category": category,
        "skip": skip,
        "limit": limit,
        "on_sale": on_sale
    }

on_sale=Noneとすることで、パラメータはオプショナルになります。型注釈により、自動的に型チェックが行われるため、バグを未然に防げます。

HTTPメソッドとステータスコード

REST APIでは、適切なHTTPメソッドとステータスコードの使い分けが重要です。FastAPIでは簡単に実装できます:

from fastapi import FastAPI, status
from pydantic import BaseModel
from typing import Optional

app = FastAPI()

class Item(BaseModel):
    name: str
    price: float

# GET - リソース取得
@app.get("/items/{item_id}")
async def read_item(item_id: int):
    return {"item_id": item_id, "name": "Sample Item"}

# POST - リソース作成
@app.post("/items/", status_code=status.HTTP_201_CREATED)
async def create_item(item: Item):
    return {"message": "Item created", "item": item}

# PUT - リソース更新(置換)
@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item):
    return {"item_id": item_id, "item": item}

# DELETE - リソース削除
@app.delete("/items/{item_id}", status_code=status.HTTP_204_NO_CONTENT)
async def delete_item(item_id: int):
    return None

status_codeパラメータで、レスポンスのHTTPステータスコードを指定できます。201 Created204 No Contentなど、RESTful APIの慣例に従った実装が可能です。

エラーハンドリング

堅牢なAPIには、適切なエラーハンドリングが必須です。FastAPIではHTTPExceptionを使って簡単に実装できます:

from fastapi import FastAPI, HTTPException

app = FastAPI()

# ダミーデータベース
items_db = {
    1: {"id": 1, "name": "Item 1"},
    2: {"id": 2, "name": "Item 2"}
}

@app.get("/items/{item_id}")
async def read_item(item_id: int):
    if item_id not in items_db:
        raise HTTPException(
            status_code=404,
            detail="Item not found"
        )
    return items_db[item_id]

@app.delete("/items/{item_id}")
async def delete_item(item_id: int):
    if item_id not in items_db:
        raise HTTPException(
            status_code=404,
            detail="Item not found"
        )
    del items_db[item_id]
    return {"message": "Item deleted"}

HTTPExceptionを発生させると、FastAPIが自動的に適切なエラーレスポンスをJSON形式で返してくれます。

非同期処理の活用

FastAPIは非同期処理に対応しており、async/awaitを使うことでスケーラブルなAPIを構築できます:

import asyncio
from fastapi import FastAPI

app = FastAPI()

@app.get("/slow-item/{item_id}")
async def read_slow_item(item_id: int):
    # 外部APIの呼び出しなど、時間がかかる処理をシミュレート
    await asyncio.sleep(2)
    return {"item_id": item_id, "processed": True}

@app.get("/fast-items/")
async def read_fast_items():
    # 複数の非同期操作を並列実行
    results = await asyncio.gather(
        asyncio.sleep(1),
        asyncio.sleep(1)
    )
    return {"message": "All items fetched", "time": "~1 second"}

非同期処理により、複数のリクエストを効率的に処理でき、APIのパフォーマンスが大幅に向上します。

CORSの設定

ブラウザからのクロスオリジンリクエストに対応する場合、CORS(Cross-Origin Resource Sharing)の設定が必要です:

from fastapi import FastAPI
from fastapi.middleware.cors import CORSMiddleware

app = FastAPI()

app.add_middleware(
    CORSMiddleware,
    allow_origins=["*"],  # 本番環境では具体的なドメインを指定
    allow_credentials=True,
    allow_methods=["*"],
    allow_headers=["*"],
)

@app.get("/items/")
async def read_items():
    return [{"id": 1, "name": "Item 1"}]

allow_origins["*"]を指定すると全て許可されますが、セキュリティ上、本番環境では具体的なドメインを指定する必要があります。

まとめ

FastAPIを使うことで、Pythonで高速で現代的なREST APIを簡単に構築できます。主なポイントは以下の通りです:

  • セットアップが簡単:FastAPIとuvicornをインストールするだけで開始可能
  • 型ヒント対応:Python 3.6+の型注釈で自動的に検証とドキュメント生成
  • 自動ドキュメント生成:Swagger UIとReDocで/docsと/redocにアクセス
  • Pydanticモデル:リクエストボディの検証と変換が自動的に実行
  • 非同期対応:async/awaitでスケーラブルなAPI開発が可能
  • エラーハンドリング:HTTPExceptionで簡潔にエラー処理を実装
  • CORS対応:ミドルウェアで容易にクロスオリジン設定が可能

FastAPIは学習曲線が緩く、同時に本番環境で使用可能な高性能なフレームワークです。今からPythonでREST API開発を始める方に、強くお勧めします。

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!
目次