Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

第1章 Web API と非同期アーキテクチャの全体像

Web アプリケーションやスマートフォンアプリは、インターネットを通じてサーバーとデータをやり取りします。その中心的な役割を果たすのが Web API サーバーです。

本章では、Web API の基本的な仕組み、従来の同期通信とモダンな非同期通信の違い、そして FastAPI、Uvicorn、Celery、Redis を組み合わせた全体アーキテクチャを学びます。

1.1 Web API とクライアント・サーバーの関係

Web API(Application Programming Interface)は、プログラム同士がネットワーク経由でデータを受け渡すための約束事です。

ブラウザやスマートフォンなどのクライアントは、HTTP リクエストをサーバーに送信します。サーバーはその要求を処理し、JSON 形式などのデータを HTTP レスポンスとして返却します。ユーザーの画面表示とサーバーのデータ処理を分離できるため、柔軟なシステム開発が可能になります。

1.2 同期処理(WSGI)と非同期処理(ASGI)

従来の Python Web アプリケーションでは、WSGI(Web Server Gateway Interface)という標準規格が使われていました。

WSGI は 1 つのリクエストを 1 つのスレッドやプロセスが専有して処理する「同期型」です。データベースへの問い合わせや外部 API 通信など、通信の待ち時間(I/O 待ち)が発生している間もプロセスが塞がってしまい、大量の同時接続を処理するには限界がありました。

一方、ASGI(Asynchronous Server Gateway Interface)は「非同期処理(async / await)」に対応した新しい規格です。通信の待ち時間が発生した際に、別のリクエストの処理へ CPU を切り替えることができるため、少ないリソースで数万規模の同時アクセスを効率よく処理できます。

graph TD
    subgraph WSGI["同期型 (WSGI)"]
        W_Req["リクエスト 1"] --> W_Wait["I/O 待ち (CPU 占有)"] --> W_Res["レスポンス 1"]
        W_Req2["リクエスト 2"] --> W_Block["待機 (前の処理が終わるまで待つ)"]
    end

    subgraph ASGI["非同期型 (ASGI)"]
        A_Req1["リクエスト 1"] --> A_Wait["I/O 待ち発生"]
        A_Wait -.->|"待ち時間に切り替え"| A_Req2["リクエスト 2 の処理開始"]
    end

1.3 FastAPI・Uvicorn・Celery・Redis の役割分担

高速で安定した Web サービスを構築するために、それぞれの得意分野に応じたコンポーネントを組み合わせて使用します。

  • Uvicorn: ASGI に準拠した Web サーバーです。クライアントからの HTTP 接続を直接受け付け、高速な非同期イベントループで FastAPI にリクエストを渡します。

  • FastAPI: Python の型ヒントを駆使した最新の Web フレームワークです。URL ルーティング、リクエストの型検証、レスポンスの生成、API 仕様書(Swagger UI)の自動生成を担当します。

  • Redis: メモリ上でデータを高速に保持するインメモリデータストアです。ここでは非同期タスクの待ち行列を管理する「メッセージブローカー」および結果の保存先として利用します。

  • Celery: 時間のかかる重い処理をバックグラウンドで非同期に実行する「分散タスクキュー」です。API サーバーとは別の独立したプロセス(ワーカー)として動作します。

1.4 システム全体のデータフローと構成図

ユーザーがアクセスしたときの全体の流れを整理します。

  1. クライアントが Uvicorn へ HTTP リクエストを送信します。
  2. Uvicorn がリクエストを FastAPI アプリケーションに渡します。
  3. 数秒以内に完了する軽量なデータ取得や更新は、FastAPI がそのまま処理して即座に応答します。
  4. 画像変換や一括メール送信、機械学習推論など数秒以上かかる重い処理は、FastAPI が Redis にタスクを投入し、タスク ID のみをクライアントに即座に返却します。
  5. 裏で待機している Celery ワーカーが Redis からタスクを取り出して実行し、完了結果を Redis に保存します。
sequenceDiagram
    autonumber
    actor Client as クライアント
    participant Uvicorn as Uvicorn (ASGI サーバー)
    participant FastAPI as FastAPI (API アプリ)
    participant Redis as Redis (Broker / Backend)
    participant Celery as Celery (ワーカー)

    Client->>Uvicorn: HTTP POST /tasks (重い処理依頼)
    Uvicorn->>FastAPI: リクエスト転送
    FastAPI->>Redis: タスクを登録 (タスク ID 発行)
    FastAPI-->>Client: 202 Accepted (タスク ID を即座に返却)
    
    par バックグラウンド実行
        Redis->>Celery: タスクを通知
        Celery->>Celery: 重い処理を実行
        Celery->>Redis: 実行結果を保存
    end

    Client->>FastAPI: HTTP GET /tasks/{task_id} (進捗確認)
    FastAPI->>Redis: 状態・結果を問い合わせ
    FastAPI-->>Client: 200 OK (進捗 or 完了結果)