当サイトは、アフィリエイト広告を利用しています
dockerコンテナを使ってFlaskのアプリケーションをGunicornのカスタムアプリケーションとして
起動する方法をまとめる。
GunicornでFlaskのWEBアプリケーションを動かす場合下記の
二つの方法がある
簡単に二つの起動方法の違いをまとめる
なので、作るアプリケーションによって使い分ける必要がある
シンプルな「Gunicornにアプリケーションインスタンスを直接渡す方法」については
下記記事で紹介している
今回はより細かな設定ができる「Gunicornのカスタムアプリケーションとして起動する方法」を
試してみる
Docker for Windowsのインストール方法については下記記事で紹介しています
プロジェクト構成は下記のようになる
.|-- Dockerfile|-- app| |-- __init__.py| |-- __main__.py| `-- app.py|-- config| `-- cfg.ini|-- docker-compose.yml`-- vscode_ex_install.sh
コンテナをdocker-composeを使って構築するための
設定を各ファイルに書いていく。
FROM python:3.12# workspaceディレクトリ作成、移動WORKDIR /workspace# プロジェクトディレクトリにコピーCOPY requirements.txt /workspace# 必要モジュールのインストールRUN pip install --upgrade pipRUN pip install -r requirements.txt
version: "3"services:sample-api:container_name: "flask_gunicorn"build:context: .dockerfile: Dockerfileports:- "5000:5000"volumes:# バインドマウント- .:/workspacetty: true
Flask==3.0.2gunicorn==21.2.0
上記を設定した上でプロジェクト直下で「docker compose up -d」を
実行すればコンテナが作成できる
$ docker compose up -d$ docker psCONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES242a4af01ee2 flask-gunicorn-sample-api "python3" 42 seconds ago Up 38 seconds 0.0.0.0:5000->5000/tcp flask_gunicorn
flaskアプリをgunicornで起動するためのコンテナができたので
flaskアプリをgunicornのカスタムアプリケーションとして実装する
cfg.iniファイルにgunicornの設定を書く
[gunicorn]bind = 0.0.0.0:5000workers = 1loglevel = info; errorlog = /var/log/error.logerrorlog = -accesslog = /var/log/access.log
__init__.pyは空ファイルで問題ない
gunicornのエントリーポイントとなるファイル。
appパッケージのエントリーポイントとするため、ファイル名は「__main__.py」
にしておく。
別名にしたい場合は起動時にモジュールまで指定する必要がある
※詳しくは後述する
from configparser import ConfigParserfrom gunicorn.app.base import BaseApplicationfrom app.app import flaskappclass AppConfig:@staticmethoddef load_config(path):# 設定ファイルからGunicornの設定取得config = ConfigParser()config.read(path)options = dict(config.items('gunicorn'))return optionsclass CustumApplication(BaseApplication):def __init__(self,app,options=None):self.options = options or {}self.application = appsuper().__init__()# Gunicornの設定をロードするdef load_config(self):for key, value in self.options.items():self.cfg.set(key.lower(), value)# Gunicornがサーブするアプリケーションインスタンスをロードするdef load(self):return self.applicationif __name__ == '__main__':# 設定ファイル読み込みoptions = AppConfig.load_config('./config/cfg.ini')# gunicornでアプリケーション起動CustumApplication(flaskapp, options).run()
アプリケーションをgunicornのカスタムアプリケーションとする場合は下記は必須で
行う必要がある
BaseApplicationはgunicornにおけるアプリケーションのベースクラスであるため
そのメソッドをオーバーライドすることでカスタムアプリケーションを作ることができる
load_configはgunicornサーバーの設定を行うためのもの。
ここでConfigParserでcfg.iniファイルから読み込んだ設定情報を
セットする
Gunicornがサーブするアプリケーションインスタンスをロードする
FlaskのREST APIを作る
今回は動作確認に使う程度なのでシンプルなものを実装する
from flask import Flask# flaskインスタンス作成flaskapp = Flask(__name__)# ディクショナリusers = [{"user_id": "1", "name": "tujimura", "age": 11},{"user_id": "2", "name": "mori", "age": 20},{"user_id": "3", "name": "shimada", "age": 50},{"user_id": "4", "name": "kyogoku", "age": 70}]@flaskapp.route('/', methods=['GET'])def get_users():# GETリクエストを処理return users
コンテナに入って実装したgunicornのカスタムアプリケーションを起動する
起動は下記のコマンドで行う
root@242a4af01ee2:/workspace# python -m app[2024-06-12 07:16:05 +0000] [23654] [INFO] Starting gunicorn 21.2.0[2024-06-12 07:16:05 +0000] [23654] [INFO] Listening at: http://0.0.0.0:5000 (23654)[2024-06-12 07:16:05 +0000] [23654] [INFO] Using worker: sync[2024-06-12 07:16:05 +0000] [23704] [INFO] Booting worker with pid: 23704
app配下に「__main__.py」があるため、コマンドではappパッケージを指定している。
エントリーポイントするファイル名が「__main__.py」出ない場合はそのモジュール名まで
指定する必要がある。
「python -m パッケージ」とした場合、pythonは指定したパッケージ内で「__main__.py」を
探し、存在すればそのスクリプトを実行する
「Gunicornにアプリケーションインスタンスを直接渡す方法」とは違い、アプリケーション経由で
Gunicornを起動するイメージ。
VScodeでデバッグする方法は下記のlaunch.jsonを作成する
{"version": "0.2.0","configurations": [{"name": "Python: Module","type": "debugpy","request": "launch","module": "app","console": "integratedTerminal","args": [],"justMyCode": false,"cwd": "${workspaceFolder}"}]}
通常の起動とデバッグ起動で同じport番号5000を使うのでデバッグする時、または通常起動する時は
もう一方が停止してから行うようにする
GunicornでFlaskのWEBアプリケーションをカスタムアプリケーションとして
起動する手順をまとめてみた。
個人的には特に複雑なことをしないようなら「Gunicornにアプリケーションインスタンスを直接渡す方法」で
作ったほうが簡単だし、わかりやすいと感じた。