はじめに
初めてやったときに若干接続するまでに手こずったので備忘録として書き残しておきます。
ディレクトリ構造は最終的に以下のようになります。
dbtest
├─ docker-compose.yml
├─ requirements.txt
│
└─blog
├─ database.py
├─ main.py
├─ models.py
├─ schemas.py
├─ settings.py
└─ __init__.py
インストールするパッケージ
requirements.txtに以下の内容を記述。
mysqlclient
sqlalchemy
uvicorn
fastapi
- mysqlclient
- mysqlをDBに使うときに必要
- sqlalchemy
- モデルとデータベースを紐づけ
- uvicorn
- サーバの起動に必要
- fastapi
- fastapiの利用に必要
以下のコマンドでインストール
pip install -r requirements.txt
接続するURL
DB接続設定で使うURLは以下のようなものになります。
# データベース作成時に設定したやつ
DB_USER = "root"
DB_PASS = "pass"
DB_NAME = "sample_db"
# 接続するホストのIPアドレス
DB_HOST = "127.0.0.1"
# 接続するポート番号
DB_PORT = "3007"
# mysql://root:pass@127.0.0.1:3007/sample_db
DATABASE_URL = f"mysql://{DB_USER}:{DB_PASS}@{DB_HOST}:{DB_PORT}/{DB_NAME}"
database設定を書き込むpythonファイルの全体像は以下のようになりました。
settings.pyに接続に必要な値は分離しています。
from sqlalchemy import create_engine
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import sessionmaker
from settings import DB_USER, DB_PASS, DB_NAME, DB_PORT, DB_HOST
DATABASE_URL = f"mysql://{DB_USER}:{DB_PASS}@{DB_HOST}:{DB_PORT}/{DB_NAME}"
engine = create_engine(DATABASE_URL)
sessionLocal = sessionmaker(bind=engine, autocommit=False, autoflush=False)
Base = declarative_base()
モデルの作成
まず、schemas.pyでスキーマを定義。
from pydantic import BaseModel
class Blog(BaseModel):
title: str
body: str
次に、モデルを記述するためのファイルを作成。ここで、String型は文字列の最大長をString(16)みたいな感じで指定しないとエラーを吐かれたので注意です。
from sqlalchemy import Column, Integer, String
from database import Base
class Blog(Base):
__tablename__ = "blogs" # テーブルの名前を明示できる
id = Column(Integer, primary_key=True, index=True)
title = Column(String(16))
body = Column(String(16))
モジュールをmain.pyで統合する。
from fastapi import FastAPI, Depends
from schemas import Blog
from models import Base
from database import engine, sessionLocal
from sqlalchemy.orm import Session
import models
app = FastAPI()
#DBテーブル作成
Base.metadata.create_all(bind=engine)
def get_db():
db = sessionLocal()
try:
yield db
finally:
db.close()
@app.post('/blog')
def create(blog: Blog, db: Session = Depends(get_db)):
new_blog = models.Blog(title=blog.title, body=blog.body)
db.add(new_blog)
db.commit()
db.refresh(new_blog)
return new_blog
MySQLコンテナを起動
docker-compose.ymlに以下の内容を記述。
version: '3'
services:
db:
image: mysql:5.7
container_name: testMysql
ports:
- "3307:3306"
environment:
MYSQL_DATABASE: sample_db
MYSQL_ROOT_USER: root
MYSQL_ROOT_PASSWORD: pass
docker-compose.ymlが直下にあるディレクトリに移動して、コンテナを立ち上げる。
docker-compose up -d
サーバーを起動
blogディレクトリに移動して、サーバーを立ち上げる。
uvicorn main:app --reload
blogsテーブルが自動生成されていることが確認できました。
ちなみに、Dockerコンテナから直接確認するには以下のようにします。
docker exec -it testMysql /bin/bash
mysql -uroot -p
//ここでパスワード求められるので、設定したものを入力
use sample_db
SHOW TABLES; //下のような図が確認できたらOK
+---------------------+
| Tables_in_sample_db |
+---------------------+
| blogs |
+---------------------+
データを送信してみる
サーバーを立ち上げた状態で以下のURLにアクセス。
http://localhost:8000/docs
次のようなページが開くので、「Try it out」をクリック。
適当な値を入力してexecute
mysqlコンテナで以下のクエリを実行してpostしたデータが登録されていたら成功。
SELECT * FROM blogs;
おわりに
Fast APIはかなり簡潔でわかりやすいなあと思いました。初心者の人はFast APIを最初に触ってから他のフレームワークに移動するって流れにしたら理解しやすくなるのでは?と感じています。