18
18

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Docker 環境で Python FastAPI Webサービスを起動する

Last updated at Posted at 2023-08-09

Docker 環境で Python FastAPI Webサービスを起動する

こんにちは、@studio_meowtoon です。今回は、WSL Ubuntu の Docker 環境で、Python FastAPI Web アプリケーションをコンテナーとして起動する方法を紹介します。
fastapi_on_docker.png

目的

Windows 11 の Linux でクラウド開発します。

こちらから記事の一覧がご覧いただけます。

実現すること

ローカル環境の WSL Ubuntu の Docker 環境で、Dockerfile からビルドした Python FastAPI Web サービスのカスタムコンテナーイメージを起動します。

Python ファイルのアプリをコンテナーとして起動

実行環境

要素 概要
terminal ターミナル
Ubuntu OS
Docker コンテナー実行環境

Web サービス コンテナー

要素 概要
app-hello-fastapi カスタムコンテナー
python Python 実行環境
main.py Python スクリプト
uvicorn Web サーバー

技術トピック

FastAPI とは?

こちらを展開してご覧いただけます。

FastAPI

FastAPI は、Python の Web フレームワークの中でもとくに注目されている新しいフレームワークであり、多くの特徴とメリットがあります。

キーワード 内容
高速な性能 FastAPI は非常に高速なWebフレームワークであり、ASGI (Asynchronous Server Gateway Interface) を活用することで高いパフォーマンスを提供します。非同期処理をサポートすることで、同時リクエストの処理が可能となります。
シンプルで直感的な記述 FastAPI はシンプルで直感的な構文を持ち、少ないコードで強力な API を構築できます。Python の型ヒント (Type Hints) を活用して、入力の検証やドキュメントの自動生成が行えます。
自動生成されたドキュメント FastAPI は Swagger UI や Redoc を使って API のドキュメントを自動生成します。API エンドポイント、リクエストボディ、レスポンスなどが自動的にドキュメント化され、API の理解やテストが容易になります。
入力検証とシリアライゼーション FastAPI はリクエストの入力データを自動的に検証し、Pydantic を使って型情報をシリアライズします。入力データのバリデーションエラーを自動的に処理できます。
依存性注入 FastAPI は依存性注入をサポートしており、依存関係の注入によってコードの再利用性とテスト容易性が向上します。依存性注入を活用することで、アプリケーションの部品を疎結合に保ちながら効果的に結合できます。
サポートされるデータベースと ORM FastAPI はさまざまなデータベースと ORM (Object-Relational Mapping) をサポートしています。たとえば、SQLAlchemy、Tortoise ORM、MongoDB、Redis などが利用可能です。
セキュリティ FastAPI は標準的なセキュリティ機能を提供しています。OAuth2.0 や API キーのサポート、HTTPS 対応など、セキュアな API の構築が可能です。

Dockerfile とは?

こちらを展開してご覧いただけます。

Dockerfile

Dockerfile は、Docker コンテナーを構築するためのテキストファイルです。Docker コンテナーはアプリケーションやサービスを実行するための環境を含む軽量でポータブルな仮想化ユニットです。

キーワード 内容
スクリプト形式 Dockerfile はシンプルなスクリプト形式で記述されるため、コンテナーのビルドプロセスを自動化することが容易です。
レイヤー構造 Docker イメージは Dockerfile の各命令が実行される際にレイヤーとして生成され、再利用やキャッシュが可能な構造となっています。
バージョン管理 Dockerfile はテキストベースであるため、コードと同様にバージョン管理システムで管理しやすいです。
ポータビリティ Dockerfile により、アプリケーションとその依存関係が1つのコンテナイメージにパッケージ化されるため、異なる環境間での移植性が高まります。
自動化と効率化 Dockerfile を使用することで、アプリケーションのビルドや環境構築を自動化できます。これにより、手動での作業時間やヒューマンエラーが減り、開発・デプロイプロセスが効率的になります。
再現性 Dockerfile はビルド手順を完全に定義するため、異なる環境で同じアプリケーションを再現できます。これにより、開発、テスト、本番環境間での一貫性が確保されます。
環境の分離 Docker コンテナーはホストシステムから分離されるため、アプリケーションの依存関係やライブラリの衝突を回避し、より安全な環境で実行できます。
拡張性 Dockerfile を使用することで、カスタムイメージを作成できます。このため、特定のニーズに合わせてカスタマイズされたコンテナイメージを容易に作成できます。

開発環境

  • Windows 11 Home 23H2 を使用しています。

WSL の Ubuntu を操作しますので macOS の方も参考にして頂けます。

WSL (Microsoft Store アプリ版) ※ こちらの関連記事からインストール方法をご確認いただけます

> wsl --version
WSL バージョン: 2.2.4.0
カーネル バージョン: 5.15.153.1-2
WSLg バージョン: 1.0.61

Ubuntu ※ こちらの関連記事からインストール方法をご確認いただけます

$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 24.04 LTS
Release:        24.04
Codename:       noble

Docker ※ こちらの関連記事からインストール方法をご確認いただけます

$ docker --version
Docker version 27.0.3, build 7d4bcd8

この記事では基本的に Ubuntu のターミナルで操作を行います。Vim を使用してコピペする方法をはじめて学ぶ人のために、以下の記事で手順を紹介しています。ぜひ挑戦してみてください。

作成する Web アプリケーションの仕様

No エンドポイント HTTPメソッド MIME タイプ
1 /api/data GET application/json

/api/data というエンドポイントに対して HTTP GET リクエストを送信すると、JSON データがレスポンスされるシンプルな Web サービスを実装します。
{"message":"Hello World!"}

Hello World を表示する手順

Python の確認

通常 Ubuntu 24.04 には、Python はプリインストールされています。

$ python3 --version
Python 3.12.3

プロジェクトの作成

プロジェクトフォルダーを作成します。
※ ~/tmp/hello-fastapi をプロジェクトフォルダーとします。

$ mkdir -p ~/tmp/hello-fastapi
$ cd ~/tmp/hello-fastapi

Python ファイルの作成

main.py Python ファイルを作成します。

$ mkdir -p app
$ vim app/main.py

ファイルの内容

app/main.py
from fastapi import FastAPI

app = FastAPI()

@app.get('/api/data')
async def get_data():
    response = {
        'message': 'Hello World!'
    }
    return response
型宣言を省略せずに記述したコード
app/main.py
from fastapi import FastAPI

app: FastAPI = FastAPI()

@app.get('/api/data')
async def get_data():
    response: dict[str, str] = {
        'message': 'Hello World!'
    }
    return response

pipx をインストールします。

$ sudo apt update
$ sudo apt install pipx

バージョンを確認します。

$ pipx --version
1.4.3

pipx ツールへの PATH を追加します。

$ pipx ensurepath

パッケージを仮想環境にインストールします。

$ pipx install uvicorn

仮想環境にパッケージを追加でインストールします。

$ pipx inject uvicorn fastapi

ローカルで実行します。
停止するときは ctrl + C を押します。

$ uvicorn app.main:app \
    --host 0.0.0.0 --port 8000

別ターミナルから curl コマンドで確認します。

$ curl -v http://localhost:8000/api/data -w '\n'

出力

* Host localhost:8000 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
*   Trying [::1]:8000...
* connect to ::1 port 8000 from ::1 port 57270 failed: 接続を拒否されました
*   Trying 127.0.0.1:8000...
* Connected to localhost (127.0.0.1) port 8000
> GET /api/data HTTP/1.1
> Host: localhost:8000
> User-Agent: curl/8.5.0
> Accept: */*
>
< HTTP/1.1 200 OK
< date: Sat, 10 Aug 2024 13:40:43 GMT
< server: uvicorn
< content-length: 26
< content-type: application/json
<
* Connection #0 to host localhost left intact
{"message":"Hello World!"}

ここまでの手順で、ターミナルに {"message":"Hello World!"} と表示され、JSON データを取得することができました。

コンテナイメージをビルド

Dockerfile を作成します。

$ vim Dockerfile

ファイルの内容

Dockerfile
# set up the container.
FROM python:3.12-slim

# set the working dir.
WORKDIR /app

# copy the app dir.
COPY app app

# install libraries.
RUN pip install --no-cache-dir fastapi uvicorn

# expose the port.
EXPOSE 8000

# command to run the app using uvicorn.
CMD ["uvicorn","app.main:app","--host","0.0.0.0","--port","8000"]
説明を開きます。
要素 説明
FROM python:3.10-slim ベースイメージとして、Python 3.10 の slim版イメージを使用します。
WORKDIR /app コンテナー内での作業ディレクトリを /app に設定します。
COPY app app: ホストマシンのカレントディレクトリにある app ディレクトリを、コンテナー内の /app ディレクトリにコピーします。
RUN pip install --no-cache-dir fastapi uvicorn 必要な Python ライブラリをインストールします。fastapi と uvicorn は、FastAPI フレームワークと ASGI サーバーのライブラリです。--no-cache-dir フラグは、キャッシュを使用せずにライブラリをインストールすることを意味します。
EXPOSE 8000 コンテナーがポート 8000 を公開することを宣言します。
CMD ["uvicorn", "app.main:app", "--host", "0.0.0.0", "--port", "8000"] コンテナー内で実行されるデフォルトのコマンドを定義します。FastAPI アプリケーションを起動するために uvicorn コマンドが使用されます。app.main:app は、FastAPI アプリケーションインスタンスを指すものです。--host 0.0.0.0 は、すべてのネットワークインターフェイスからの接続を許可することを意味し、--port 8000 は uvicorn がリッスンするポート番号を指定します。

Docker デーモンを起動します。

$ sudo service docker start

Docker 環境をお持ちでない場合は、以下の関連記事から Docker Engine のインストール手順をご確認いただけます。

コンテナイメージをビルドします。

$ docker build \
    --no-cache \
    --tag app-hello-fastapi:latest .

コンテナイメージを確認します。

$ docker images | grep app-hello-fastapi
app-hello-fastapi    latest    c31921620823   53 seconds ago   153MB

ここまでの手順で、ローカル環境の Docker にアプリのカスタムコンテナイメージをビルドすることができました。

コンテナーを起動

ローカルでコンテナーを起動します。
※ コンテナーを停止するときは ctrl + C を押します。

$ docker run --rm \
    --publish 8000:8000 \
    --name app-local \
    app-hello-fastapi:latest

ここまでの手順で、ローカル環境の Docker でアプリのカスタムコンテナーを起動することができました。

コンテナーの動作確認

別ターミナルから curl コマンドで確認します。

$ curl -v http://localhost:8000/api/data -w '\n'

出力

* Host localhost:8000 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
*   Trying [::1]:8000...
* Connected to localhost (::1) port 8000
> GET /api/data HTTP/1.1
> Host: localhost:8000
> User-Agent: curl/8.5.0
> Accept: */*
>
< HTTP/1.1 200 OK
< date: Sat, 10 Aug 2024 14:23:23 GMT
< server: uvicorn
< content-length: 26
< content-type: application/json
<
* Connection #0 to host localhost left intact
{"message":"Hello World!"}

ここまでの手順で、ターミナルに {"message":"Hello World!"} と表示され、JSON データを取得することができました。

コンテナーの状態を確認してみます。

$ docker ps
CONTAINER ID   IMAGE                      COMMAND                   CREATED          STATUS          PORTS                                       NAMES
a132ae388071   app-hello-fastapi:latest   "uvicorn app.main:ap…"   22 seconds ago   Up 21 seconds   0.0.0.0:8000->8000/tcp, :::8000->8000/tcp   app-local

コンテナーに接続

別ターミナルからコンテナーに接続します。

$ docker exec -it app-local /bin/sh

コンテナー接続後にディレクトリを確認します。
※ コンテナーから出るときは ctrl + D を押します。

# pwd
/app
# ls -lah
total 12K
drwxr-xr-x 1 root root 4.0K Aug 10 14:21 .
drwxr-xr-x 1 root root 4.0K Aug 10 14:24 ..
drwxr-xr-x 3 root root 4.0K Aug 10 13:26 app

top コマンドで状況を確認します。

# apt update
# apt install procps
# top
top - 14:26:44 up  2:11,  0 user,  load average: 0.11, 0.07, 0.01
Tasks:   3 total,   1 running,   2 sleeping,   0 stopped,   0 zombie
%Cpu(s):  0.0 us,  0.1 sy,  0.0 ni, 99.9 id,  0.0 wa,  0.0 hi,  0.0 si,  0.0 st
MiB Mem :  15949.2 total,  14997.9 free,    825.5 used,    403.4 buff/cache
MiB Swap:   4096.0 total,   4096.0 free,      0.0 used.  15123.7 avail Mem

    PID USER      PR  NI    VIRT    RES    SHR S  %CPU  %MEM     TIME+ COMMAND
      1 root      20   0   55068  48880  14176 S   0.3   0.3   0:00.75 uvicorn
      7 root      20   0    2576    892    800 S   0.0   0.0   0:00.00 sh
    175 root      20   0    8992   4732   2860 R   0.0   0.0   0:00.00 top

コンテナーの情報を表示してみます。

# cat /etc/*-release
PRETTY_NAME="Debian GNU/Linux 12 (bookworm)"
NAME="Debian GNU/Linux"
VERSION_ID="12"
VERSION="12 (bookworm)"
VERSION_CODENAME=bookworm
ID=debian
HOME_URL="https://www.debian.org/"
SUPPORT_URL="https://www.debian.org/support"
BUG_REPORT_URL="https://bugs.debian.org/"

このコンテナーは Debian GNU/Linux をベースに作成されています。つまり、Debian GNU/Linux と同じように扱うことができます。

ディレクトリ・ファイル構成

プロジェクトのファイル構成を表示してみます。

$ tree -I '__pycache__'
.
├── Dockerfile
└── app
    └── main.py

まとめ

WSL Ubuntu の Docker 環境で、Dockerfile からビルドした Python FastAPI Web サービスのカスタムコンテナーを起動することができました。

クラウド開発においては、Dockerfile の理解は重要です。自動ビルドツールもありますが、手動で書く必要があるケースもあります。Ubuntu を使うと Linux の知識も身に付きます。最初は難しく感じるかもしれませんが、徐々に進めていけば自信を持って書けるようになります。

どうでしたか? WSL Ubuntu で、Python FastAPI Web アプリケーションを手軽に実行できます。ぜひお試しください。今後も Python の開発環境などを紹介しますので、ぜひお楽しみにしてください。

推奨コンテンツ

18
18
3

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
18
18

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?