Python の Webフレームワーク。
以下、公式より引用 ( https://fastapi.tiangolo.com/ja/ )
高速: NodeJS や Go 並みのとても高いパフォーマンス (Starlette と Pydantic のおかげです)。 最も高速な Python フレームワークの一つです。
高速なコーディング: 開発速度を約 200%~300%向上させます。
「NodeJS や Go 並みのとても高いパフォーマンス」というのは本当か。
個人的には、ルーティングに関しては、そこそこのパフォーマンスは出せるかもしれないが、
ビジネスロジックをゴリゴリ書く場合、限界があるのではないかと推測。(検証が必要)
pip install fastapi
本番環境ではASGI サーバーが必要(以下では Uvicorn を使用)
pip install "uvicorn[standard]"
from fastapi import FastAPI
app = FastAPI()
@app.get("/")
def read_root():
return {"Hello": "World"}
@app.get("/items/{item_id}")
def read_item(item_id: int, q: str = None):
return {"item_id": item_id, "q": q}
uvicorn main:app --reload
尚、以下のURLでAPIドキュメントを表示可能。
http://127.0.0.1:8000/docs ( Swagger UI )
http://127.0.0.1:8000/redoc ( ReDoc )
例)
from fastapi import FastAPI
from fastapi.responses import JSONResponse
from pydantic import BaseModel, Field
app = FastAPI()
# 動作確認用
class DataHolder:
items = [
{"item_id": "item01", "item_name": "アイテム01", "description": "説明01"},
{"item_id": "item02", "item_name": "アイテム02", "description": "説明02"},
{"item_id": "item03", "item_name": "アイテム03", "description": "説明03"},
]
class Item(BaseModel):
item_id: str
item_name: str
description: str | None = None
@app.get("/")
def root():
return {"message": "this is root"}
@app.get("/items")
def read_items(item_name: str = None): # メソッド引数でクエリ文字列の取得が可能
if item_name:
return [i for i in items if i["item_name"] == item_name]
return DataHolder.items
@app.get("/items/{item_id}") # PATHパラメータは {項目名} で取得可能
def read_item(item_id):
matched = [i for i in DataHolder.items if i["item_id"] == item_id]
if matched:
return matched[0]
return JSONResponse(status_code=404, content={"message": "該当データなし"})
@app.post("/items", status_code=201) # デフォルトのステータス宣言
def new_item(new_item: Item): # BaseModelを継承したclassで入力データの取得が可能
if len([i for i in DataHolder.items if i["item_id"] == new_item.item_id]) > 0:
return JSONResponse(status_code=400, content={"message": "既に登録されています"}) # 任意のステータスを返却する場合
DataHolder.items.append(new_item.dict())
return new_item
@app.put("/items/{item_id}")
def update_item(item_id: str, item: Item):
if len([i for i in DataHolder.items if i["item_id"] == item_id]) == 0:
return JSONResponse(status_code=404, content={"message": "該当データなし"})
upd_item = { "item_id": item_id, "item_name": item.item_name, "description": item.description }
DataHolder.items = [upd_item if i["item_id"] == item_id else i for i in DataHolder.items]
return {"message": "updated"}
@app.delete("/items/{item_id}")
def delete_item(item_id: str):
if len([i for i in DataHolder.items if i["item_id"] == item_id]) == 0:
return JSONResponse(status_code=404, content={"message": "該当データなし"})
DataHolder.items = [i for i in DataHolder.items if i["item_id"] != item_id]
return {"message": "deleted"}