跳至內容

擴展 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 描述,可以包含 Markdown 語法,並會顯示在文件中。
  • 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.dev.org.tw/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.dev.org.tw/img/logo-margin/logo-teal.png"
    }
    app.openapi_schema = openapi_schema
    return app.openapi_schema


app.openapi = custom_openapi

修改 OpenAPI 模式

現在您可以新增 ReDoc 擴充功能,將自訂 x-logo 新增到 OpenAPI 模式中的 info「物件」

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.dev.org.tw/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.dev.org.tw/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.dev.org.tw/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 的標誌)