yasudacloudの日記

札幌に住むソフトウェアエンジニア

【前編】FastAPIとReactでダブルホットリロード

FastAPIについて

フロントエンドとバックエンドを同時に実装しているとコードの共通化に悩む時があります。

WebアプリであればWebAPIの定義やエラーメッセージ、アプリケーション固有の定数等が想像しやすいと思います。その中でもWebAPIは開発から運用フェーズまで変更が起きやすく、重要度が高いと言えます。

 

そんな時、FastAPIのOpenAPI自動生成を利用すると悩みが解決するかもしれません。FastAPIではAPIの実装を元にSwagger UIのドキュメントを自動生成してくれます。加えて、起動時のオプションで--reloadを設定するとホットリロードが効くため開発者が直接YamlJSONに手を入れる必要がありません。

生成されるのはSwaggerのHTMLだけでなくOpenAPIのJSONにもアクセスできるためこれを元にクライアント側の実装を生成することが可能になります。最近のWebFWは便利ですね。

今回の記事(前編と後編)ではフロントエンドとバックエンドのホットリロードを組み合わせて、FastAPIの更新→クライアント(React)の自動更新まで試してみたいと思います。

ちなみに、似たような動きとしてNestJS(TypeScript WebFW)でも同様に実装からSwaggerを生成することは可能ですがFastAPIと比べるとやや重たいかもしれません。

 

Swagger

FastAPIを起動して/docsを開くと既にSwaggerが作られています。画像にもあるように/openapi.jsonを開くとスキーマを確認することができます。

f:id:yasudacloud:20220317230123p:plain

Reactのセットアップ

たまたまWebStormを開いていたのでクライアント側はReactで実装します。

まず、Reactのプロジェクトを作成してプロジェクトルートにOpenAPIのクライアントコードを出力してみます。型を使いたいのでTypeScriptを選びます。

 

npm install -g @openapitools/openapi-generator-cli
mkdir ./http
openapi-generator-cli generate -i http://127.0.0.1:8000/openapi.json -g typescript-axios -o ./src/http

 

この時点で、TypeScriptのReactのsrcの中にOpenAPIのクライアントコードが出来ます。srcの外に作ろうとするとエラーになるので注意です。

 

では次にFastAPIのインストール時に作られているAPIを実行してみます。正しくセットアップができた場合はApp.tsxから./httpのソースをimportすることが可能なはずです。

 

import * as api from './http/api'

function App() {
const onClick = async () => {
const client = api.DefaultApiFactory(undefined, 'http://localhost:8000')
const response = await client.rootGet()
console.log(response.data)
}

return (
<div className="App">
<div style={{margin: 100}}>
<button onClick={onClick}>APIを叩く</button>
</div>
</div>
);
}

 

ポイントclient.rootGet()のところで、WebAPIの定義が関数として生成されていることがわかります。

これを実行するとこのようになります。

f:id:yasudacloud:20220317234856g:plain

 

これだけではReactからOpenAPIを使ってHTTPリクエストを叩いただけですね。

次回は掲題のダブルホットリロードに挑戦してみたいと思います。

 

以上、前編でした٩( ᐛ )و