Welcome to Tech Athletes | テック・アスリート   Click to listen highlighted text! Welcome to Tech Athletes | テック・アスリート

【2026年最新】Python + FastAPIで作るモダンなWebAPI完全ガイド|インストールから本番デプロイまで

FastAPIとは?Pythonの次世代Webフレームワーク

FastAPIは、Python 3.7以上で動作する高速なWebフレームワークです。Django REST frameworkやFlaskと比較して、最大300%以上のパフォーマンス向上が期待でき、自動ドキュメント生成機能を標準搭載しています。2024〜2025年にかけてGitHubスターが急増しており、エンジニアから最も注目されているWebフレームワークの一つです。

FastAPIの主な特徴・メリット

  • 高速性:Starlette(ASGI)ベースで非同期処理に対応。Node.jsやGoに匹敵するパフォーマンス
  • 型安全性:Pydanticによるデータバリデーションで、実行時エラーを防ぐ
  • 自動ドキュメント:Swagger UIとReDocが標準搭載。APIドキュメントを自動生成
  • 依存性注入:クリーンな依存性注入システムで、テストしやすいコードを書ける
  • OpenAPI準拠:標準規格に準拠しているため、フロントエンドとの連携が容易

FastAPIのインストールと環境構築

まずPython仮想環境を作成してFastAPIをインストールします。

# 仮想環境の作成とアクティベート
python -m venv venv
source venv/bin/activate  # Windows: venvScriptsactivate

# FastAPIとuvicornをインストール
pip install fastapi uvicorn[standard] pydantic

# 開発用ツールも追加
pip install httpx pytest

最初のFastAPI WebAPIを作成する

以下のコードで基本的なREST APIを作成できます。main.pyというファイルを作成し、以下を記述してください。

from fastapi import FastAPI, HTTPException, Depends
from pydantic import BaseModel
from typing import List, Optional
from datetime import datetime

app = FastAPI(
    title="Tech Athletes API",
    description="エンジニア向けサンプルAPI",
    version="1.0.0"
)

# Pydanticモデル(リクエスト・レスポンスの型定義)
class ArticleCreate(BaseModel):
    title: str
    content: str
    author: str
    tags: Optional[List[str]] = []

class ArticleResponse(BaseModel):
    id: int
    title: str
    content: str
    author: str
    tags: List[str]
    created_at: datetime

# インメモリデータストア(本番ではDBを使用)
articles_db = []
article_id_counter = 1

@app.get("/", tags=["ルート"])
def read_root():
    return {"message": "Tech Athletes API へようこそ!", "docs": "/docs"}

@app.get("/articles", response_model=List[ArticleResponse], tags=["記事"])
def get_articles(skip: int = 0, limit: int = 10):
    """記事一覧を取得します"""
    return articles_db[skip:skip + limit]

@app.post("/articles", response_model=ArticleResponse, status_code=201, tags=["記事"])
def create_article(article: ArticleCreate):
    """新しい記事を作成します"""
    global article_id_counter
    new_article = ArticleResponse(
        id=article_id_counter,
        title=article.title,
        content=article.content,
        author=article.author,
        tags=article.tags,
        created_at=datetime.now()
    )
    articles_db.append(new_article)
    article_id_counter += 1
    return new_article

@app.get("/articles/{article_id}", response_model=ArticleResponse, tags=["記事"])
def get_article(article_id: int):
    """特定の記事を取得します"""
    for article in articles_db:
        if article.id == article_id:
            return article
    raise HTTPException(status_code=404, detail="記事が見つかりません")

APIサーバーの起動方法

# 開発サーバーを起動(ホットリロード有効)
uvicorn main:app --reload --host 0.0.0.0 --port 8000

# 本番環境での起動(ワーカー数を増やす)
uvicorn main:app --workers 4 --host 0.0.0.0 --port 8000

サーバー起動後、http://localhost:8000/docsにアクセスするとSwagger UIが表示され、ブラウザ上でAPIをテストできます。

Pydanticによるバリデーションの活用

Pydanticを使うと、入力データのバリデーションを型ヒントだけで実現できます。

from pydantic import BaseModel, EmailStr, validator, Field
from typing import Optional

class UserRegister(BaseModel):
    username: str = Field(..., min_length=3, max_length=20, description="ユーザー名(3〜20文字)")
    email: EmailStr
    age: Optional[int] = Field(None, ge=0, le=120)
    bio: Optional[str] = Field(None, max_length=500)
    
    @validator('username')
    def username_alphanumeric(cls, v):
        if not v.replace('_', '').isalnum():
            raise ValueError('ユーザー名は英数字とアンダースコアのみ使用可能です')
        return v

# 使用例
@app.post("/users/register")
def register_user(user: UserRegister):
    # バリデーション済みのデータが来るので安全に処理できる
    return {"message": f"ユーザー {user.username} を登録しました"}

依存性注入(Dependency Injection)の活用

FastAPIの依存性注入機能を使うと、認証処理や共通ロジックをクリーンに実装できます。

from fastapi import Depends, HTTPException, Header
from typing import Optional

# 認証用の依存関数
async def verify_token(authorization: Optional[str] = Header(None)):
    if not authorization or not authorization.startswith("Bearer "):
        raise HTTPException(status_code=401, detail="認証トークンが必要です")
    token = authorization.split(" ")[1]
    # 実際の実装ではJWT検証などを行う
    if token != "valid-token":
        raise HTTPException(status_code=401, detail="無効なトークンです")
    return {"user_id": 1, "username": "kasata"}

# 認証が必要なエンドポイント
@app.get("/protected", tags=["認証"])
async def protected_route(current_user: dict = Depends(verify_token)):
    return {"message": f"こんにちは、{current_user['username']}さん!"}

データベース連携(SQLAlchemy + SQLite)

本番環境ではデータベースと連携します。SQLAlchemyを使ったパターンを紹介します。

pip install sqlalchemy databases aiosqlite
from sqlalchemy import create_engine, Column, Integer, String, DateTime
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import sessionmaker, Session
from datetime import datetime

DATABASE_URL = "sqlite:///./tech_athletes.db"
engine = create_engine(DATABASE_URL, connect_args={"check_same_thread": False})
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
Base = declarative_base()

class ArticleModel(Base):
    __tablename__ = "articles"
    
    id = Column(Integer, primary_key=True, index=True)
    title = Column(String(200), nullable=False)
    content = Column(String, nullable=False)
    author = Column(String(100), nullable=False)
    created_at = Column(DateTime, default=datetime.now)

# テーブル作成
Base.metadata.create_all(bind=engine)

# DBセッションの依存関数
def get_db():
    db = SessionLocal()
    try:
        yield db
    finally:
        db.close()

@app.get("/db-articles")
def get_db_articles(db: Session = Depends(get_db)):
    return db.query(ArticleModel).all()

FastAPIのテスト方法

FastAPIはテストが書きやすい構造になっています。pytestとhttpxを使ったテスト例です。

from fastapi.testclient import TestClient
from main import app

client = TestClient(app)

def test_root():
    response = client.get("/")
    assert response.status_code == 200
    assert "message" in response.json()

def test_create_article():
    article_data = {
        "title": "テスト記事",
        "content": "テストコンテンツ",
        "author": "テストユーザー",
        "tags": ["python", "fastapi"]
    }
    response = client.post("/articles", json=article_data)
    assert response.status_code == 201
    data = response.json()
    assert data["title"] == "テスト記事"

def test_get_nonexistent_article():
    response = client.get("/articles/99999")
    assert response.status_code == 404

本番デプロイ:Dockerを使ったコンテナ化

本番環境ではDockerを使ってコンテナ化するのが一般的です。

# Dockerfile
FROM python:3.11-slim

WORKDIR /app

COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

COPY . .

CMD ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]
# docker-compose.yml
version: '3.8'

services:
  api:
    build: .
    ports:
      - "8000:8000"
    environment:
      - DATABASE_URL=postgresql://user:password@db:5432/techdb
    depends_on:
      - db
  
  db:
    image: postgres:15
    environment:
      - POSTGRES_USER=user
      - POSTGRES_PASSWORD=password
      - POSTGRES_DB=techdb
    volumes:
      - postgres_data:/var/lib/postgresql/data

volumes:
  postgres_data:

まとめ:FastAPIでWebAPI開発を始めよう

FastAPIは、Pythonで高性能なWebAPIを構築したいエンジニアに最適なフレームワークです。主なポイントをまとめると:

  • 型ヒントベースで書きやすく、バグが少ない
  • 自動ドキュメント生成でAPI仕様書が不要
  • 非同期処理対応で高パフォーマンス
  • Dockerとの親和性が高く、本番デプロイが容易
  • テストが書きやすく、品質を保ちやすい

次のステップとして、AWS LambdaやGoogle Cloud RunへのデプロイJWT認証の実装Redis キャッシュの活用なども検討してみてください。関連記事も参考にどうぞ。


💡 関連記事DockerとKubernetesで学ぶコンテナ基礎AWS LambdaでPythonサーバーレス入門

投稿者 kasata

IT企業でエンジニアとして勤務後、テクノロジー情報メディア「Tech Athletes(テック・アスリート)」を運営。プログラミング、クラウドインフラ(AWS/GCP/Azure)、AI活用、Webサービス開発を専門とする。エンジニア・ビジネスパーソン向けに、実際に使ってみた経験をもとに信頼できる技術情報を発信中。資格:AWS認定ソリューションアーキテクト、Python 3 エンジニア認定試験合格。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

Click to listen highlighted text!