OpenAPIの拡張¶
生成されたOpenAPIスキーマを変更する必要がある場合があります。
このセクションでは、その方法について説明します。
通常のプロセス¶
通常の(デフォルトの)プロセスは次のとおりです。
FastAPI
アプリケーション(インスタンス)には、OpenAPIスキーマを返すことが期待される.openapi()
メソッドがあります。
アプリケーション オブジェクトの作成の一環として、/openapi.json
(またはopenapi_url
に設定したパス)の*パス操作*が登録されます。
これは、アプリケーションの.openapi()
メソッドの結果を含むJSONレスポンスを返すだけです。
デフォルトでは、.openapi()
メソッドは、プロパティ.openapi_schema
にコンテンツがあるかどうかを確認し、それらを返します。
コンテンツがない場合は、fastapi.openapi.utils.get_openapi
にあるユーティリティ関数を使用して生成します。
そして、その関数get_openapi()
はパラメータとして以下を受け取ります。
title
: OpenAPIのタイトル。ドキュメントに表示されます。version
: APIのバージョン。例:2.5.0
。openapi_version
: 使用されるOpenAPI仕様のバージョン。デフォルトでは最新バージョン:3.1.0
。summary
: APIの簡単な概要。description
: APIの説明。マークダウンを含めることができ、ドキュメントに表示されます。routes
: ルートのリスト。これらはそれぞれ登録された*パス操作*です。app.routes
から取得されます。
情報
パラメータsummary
はOpenAPI 3.1.0以上で使用可能で、FastAPI 0.99.0以上でサポートされています。
デフォルトのオーバーライド¶
上記の情報を使用して、同じユーティリティ関数を使用してOpenAPIスキーマを生成し、必要な部分をオーバーライドできます。
たとえば、カスタム ロゴを含めるためのReDocのOpenAPI拡張を追加してみましょう。
通常のFastAPI¶
まず、すべてのFastAPIアプリケーションを通常どおり記述します。
from fastapi import FastAPI
from fastapi.openapi.utils import get_openapi
app = FastAPI()
@app.get("/items/")
async def read_items():
return [{"name": "Foo"}]
def custom_openapi():
if app.openapi_schema:
return app.openapi_schema
openapi_schema = get_openapi(
title="Custom title",
version="2.5.0",
summary="This is a very custom OpenAPI schema",
description="Here's a longer description of the custom **OpenAPI** schema",
routes=app.routes,
)
openapi_schema["info"]["x-logo"] = {
"url": "https://fastapi.dokyumento.jp/img/logo-margin/logo-teal.png"
}
app.openapi_schema = openapi_schema
return app.openapi_schema
app.openapi = custom_openapi
OpenAPIスキーマの生成¶
次に、custom_openapi()
関数内で同じユーティリティ関数を使用してOpenAPIスキーマを生成します。
from fastapi import FastAPI
from fastapi.openapi.utils import get_openapi
app = FastAPI()
@app.get("/items/")
async def read_items():
return [{"name": "Foo"}]
def custom_openapi():
if app.openapi_schema:
return app.openapi_schema
openapi_schema = get_openapi(
title="Custom title",
version="2.5.0",
summary="This is a very custom OpenAPI schema",
description="Here's a longer description of the custom **OpenAPI** schema",
routes=app.routes,
)
openapi_schema["info"]["x-logo"] = {
"url": "https://fastapi.dokyumento.jp/img/logo-margin/logo-teal.png"
}
app.openapi_schema = openapi_schema
return app.openapi_schema
app.openapi = custom_openapi
OpenAPIスキーマの変更¶
これで、ReDoc拡張機能を追加し、OpenAPIスキーマのinfo
「オブジェクト」にカスタムx-logo
を追加できます。
from fastapi import FastAPI
from fastapi.openapi.utils import get_openapi
app = FastAPI()
@app.get("/items/")
async def read_items():
return [{"name": "Foo"}]
def custom_openapi():
if app.openapi_schema:
return app.openapi_schema
openapi_schema = get_openapi(
title="Custom title",
version="2.5.0",
summary="This is a very custom OpenAPI schema",
description="Here's a longer description of the custom **OpenAPI** schema",
routes=app.routes,
)
openapi_schema["info"]["x-logo"] = {
"url": "https://fastapi.dokyumento.jp/img/logo-margin/logo-teal.png"
}
app.openapi_schema = openapi_schema
return app.openapi_schema
app.openapi = custom_openapi
OpenAPIスキーマのキャッシュ¶
プロパティ.openapi_schema
を「キャッシュ」として使用して、生成されたスキーマを格納できます。
こうすることで、ユーザーがAPIドキュメントを開くたびにアプリケーションがスキーマを生成する必要がなくなります。
スキーマは一度だけ生成され、次回のリクエストには同じキャッシュされたスキーマが使用されます。
from fastapi import FastAPI
from fastapi.openapi.utils import get_openapi
app = FastAPI()
@app.get("/items/")
async def read_items():
return [{"name": "Foo"}]
def custom_openapi():
if app.openapi_schema:
return app.openapi_schema
openapi_schema = get_openapi(
title="Custom title",
version="2.5.0",
summary="This is a very custom OpenAPI schema",
description="Here's a longer description of the custom **OpenAPI** schema",
routes=app.routes,
)
openapi_schema["info"]["x-logo"] = {
"url": "https://fastapi.dokyumento.jp/img/logo-margin/logo-teal.png"
}
app.openapi_schema = openapi_schema
return app.openapi_schema
app.openapi = custom_openapi
メソッドのオーバーライド¶
これで、.openapi()
メソッドを新しい関数に置き換えることができます。
from fastapi import FastAPI
from fastapi.openapi.utils import get_openapi
app = FastAPI()
@app.get("/items/")
async def read_items():
return [{"name": "Foo"}]
def custom_openapi():
if app.openapi_schema:
return app.openapi_schema
openapi_schema = get_openapi(
title="Custom title",
version="2.5.0",
summary="This is a very custom OpenAPI schema",
description="Here's a longer description of the custom **OpenAPI** schema",
routes=app.routes,
)
openapi_schema["info"]["x-logo"] = {
"url": "https://fastapi.dokyumento.jp/img/logo-margin/logo-teal.png"
}
app.openapi_schema = openapi_schema
return app.openapi_schema
app.openapi = custom_openapi
確認¶
http://127.0.0.1:8000/redocにアクセスすると、カスタム ロゴ(この例ではFastAPIのロゴ)を使用していることがわかります。