跳至內容

FastAPI

FastAPI

FastAPI 框架,高效能、易學、快速編碼、可立即投入生產環境

Test Coverage Package version Supported Python versions


文件https://fastapi.dev.org.tw

原始碼https://github.com/fastapi/fastapi


FastAPI 是一個現代化、快速(高效能)的網頁框架,用於使用 Python 構建 API,基於標準 Python 類型提示。

主要特色:

  • 快速:非常高性能,與 NodeJSGo 並駕齊驅(歸功於 Starlette 和 Pydantic)。Python 框架中速度最快的之一
  • 快速編碼:將開發功能的速度提高約 200% 至 300%。*
  • 更少錯誤:減少約 40% 的人為(開發人員)錯誤。*
  • 直覺:優秀的編輯器支援。自動完成 無處不在。更少除錯時間。
  • 簡單:易於使用和學習。更少閱讀文件的時間。
  • 簡潔:最大限度地減少程式碼重複。每個參數宣告都具有多項功能。更少錯誤。
  • 穩健:獲得可投入生產環境的程式碼。具有自動互動式文件。
  • 基於標準:基於(並且完全相容)API 的開放標準:OpenAPI(以前稱為 Swagger)和 JSON Schema

* 基於內部開發團隊構建生產應用程式的測試估計。

贊助商

其他贊助商

評價

[...] 我最近經常使用 FastAPI。[...] 我實際上計劃將它用於我們團隊在 微軟 的所有 機器學習服務。其中一些正被整合到核心 Windows 產品和一些 Office 產品中。

Kabir Khan - 微軟 (參考)

我們採用了 FastAPI 函式庫來產生一個 REST 伺服器,可以查詢該伺服器來獲得 預測。[針對 Ludwig]

Piero Molino、Yaroslav Dudin 和 Sai Sumanth Miryala - Uber (參考)

Netflix 很高興地宣布開源發布我們的 危機管理 協調框架:Dispatch![使用 FastAPI 構建]

Kevin Glisson、Marc Vilanova、Forest Monsen - Netflix (參考)

我對 FastAPI 欣喜若狂。它太有趣了!

Brian Okken - Python Bytes 播客主持人 (參考)

老實說,你構建的東西看起來非常紮實和精緻。在許多方面,這正是我希望 Hug 成為的樣子——看到有人構建它真的很有啟發性。

Timothy Crosley - Hug 的創作者 (參考)

如果你正在尋找一個學習構建 REST API 的 現代框架,請查看 FastAPI [...] 它快速、易於使用且易於學習 [...]

我們已經將API全面轉換到FastAPI [...] 我想你會喜歡的 [...]

Ines Montani - Matthew Honnibal - Explosion AI 創辦人 - spaCy 的創造者 (參考) - (參考)

如果有人正在尋找構建一個正式環境的 Python API,我會強烈推薦FastAPI。它的設計精美使用簡單高度可擴展,它已成為我們 API 優先開發策略中的關鍵組成部分,並驅動許多自動化和服務,例如我們的虛擬 TAC 工程師。

Deon Pillsbury - 思科 (參考)

Typer,CLI 的 FastAPI

如果您正在構建一個要在終端機中使用的CLI應用程式,而不是 Web API,請查看 Typer

Typer 是 FastAPI 的小兄弟。它的目標是成為 CLI 的 FastAPI。 ⌨️ 🚀

需求

FastAPI 站在巨人的肩膀上

安裝

建立並啟動一個 虛擬環境,然後安裝 FastAPI

$ pip install "fastapi[standard]"

---> 100%

注意:請確保將 "fastapi[standard]" 放在引號中,以確保它在所有終端機中都能正常運作。

範例

建立它

  • 使用以下程式碼建立一個名為 main.py 的檔案
from typing import Union

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: Union[str, None] = None):
    return {"item_id": item_id, "q": q}
或者使用 async def...

如果您的程式碼使用 async / await,請使用 async def

from typing import Union

from fastapi import FastAPI

app = FastAPI()


@app.get("/")
async def read_root():
    return {"Hello": "World"}


@app.get("/items/{item_id}")
async def read_item(item_id: int, q: Union[str, None] = None):
    return {"item_id": item_id, "q": q}

注意事項:

如果您不清楚,請查看文件中關於 asyncawait 的「趕時間嗎?」 部分。

執行它

使用以下指令執行伺服器

$ fastapi dev main.py

 ╭────────── FastAPI CLI - Development mode ───────────╮
 │                                                     │
 │  Serving at: http://127.0.0.1:8000                  │
 │                                                     │
 │  API docs: http://127.0.0.1:8000/docs               │
 │                                                     │
 │  Running in development mode, for production use:   │
 │                                                     │
 │  fastapi run                                        │
 │                                                     │
 ╰─────────────────────────────────────────────────────╯

INFO:     Will watch for changes in these directories: ['/home/user/code/awesomeapp']
INFO:     Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)
INFO:     Started reloader process [2248755] using WatchFiles
INFO:     Started server process [2248757]
INFO:     Waiting for application startup.
INFO:     Application startup complete.
關於指令 fastapi dev main.py...

指令 fastapi dev 會讀取您的 main.py 檔案,偵測其中的 FastAPI 應用程式,並使用 Uvicorn 啟動伺服器。

預設情況下,fastapi dev 將在啟用自動重新載入的狀態下啟動,以便進行本地開發。

您可以在 FastAPI CLI 文件 中閱讀更多相關資訊。

檢查它

在您的瀏覽器中開啟 http://127.0.0.1:8000/items/5?q=somequery

您將看到如下 JSON 回應

{"item_id": 5, "q": "somequery"}

您已經建立了一個 API,它可以

  • 接收路徑 //items/{item_id} 的 HTTP 請求。
  • 兩個路徑都接受 GET 操作(也稱為 HTTP 方法)。
  • 路徑 /items/{item_id} 有一個路徑參數 item_id,它應該是一個 int
  • 路徑 /items/{item_id} 有一個可選的 str 查詢參數 q

互動式 API 文件

現在前往 http://127.0.0.1:8000/docs

您將看到自動互動式 API 文件(由 Swagger UI 提供)

Swagger UI

替代 API 文件

現在,請前往 http://127.0.0.1:8000/redoc

您將看到替代的自動文件(由 ReDoc 提供)

ReDoc

升級範例

現在修改檔案 main.py 以從 PUT 請求接收主體。

使用標準 Python 類型宣告主體,這要歸功於 Pydantic。

from typing import Union

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


class Item(BaseModel):
    name: str
    price: float
    is_offer: Union[bool, None] = None


@app.get("/")
def read_root():
    return {"Hello": "World"}


@app.get("/items/{item_id}")
def read_item(item_id: int, q: Union[str, None] = None):
    return {"item_id": item_id, "q": q}


@app.put("/items/{item_id}")
def update_item(item_id: int, item: Item):
    return {"item_name": item.name, "item_id": item_id}

fastapi dev 伺服器應該會自動重新載入。

互動式 API 文件升級

現在前往 http://127.0.0.1:8000/docs

  • 互動式 API 文件將會自動更新,包含新的主體

Swagger UI

  • 點擊「試用」按鈕,它允許您填寫參數並直接與 API 互動

Swagger UI interaction

  • 然後點擊「執行」按鈕,使用者介面將與您的 API 進行通訊,發送參數,取得結果並顯示在螢幕上

Swagger UI interaction

替代 API 文件升級

現在,請前往 http://127.0.0.1:8000/redoc

  • 替代文件也會反映新的查詢參數和主體

ReDoc

摘要

總而言之,您只需一次性宣告參數、主體等的類型作為函式參數。

您可以使用標準的現代 Python 類型來完成此操作。

您不必學習新的語法、特定函式庫的方法或類別等等。

只需標準的 Python

例如,對於 int

item_id: int

或者對於更複雜的 Item 模型

item: Item

...並且只需單次宣告,您就可以獲得

  • 編輯器支援,包含
    • 自動完成。
    • 類型檢查。
  • 資料驗證
    • 當資料無效時,會自動顯示清楚的錯誤訊息。
    • 即使是深度嵌套的 JSON 物件也能進行驗證。
  • 輸入資料的轉換:從網路資料轉換為 Python 資料和類型。從以下來源讀取
    • JSON。
    • 路徑參數。
    • 查詢參數。
    • Cookie。
    • 標頭。
    • 表單。
    • 檔案。
  • 輸出資料的轉換:將 Python 資料和類型轉換為網路資料(例如 JSON)
    • 轉換 Python 類型(strintfloatboollist 等等)。
    • datetime 物件。
    • UUID 物件。
    • 資料庫模型。
    • ...以及更多其他類型。
  • 自動互動式 API 文件,包含 2 種替代使用者介面
    • Swagger UI。
    • ReDoc。

回到先前的程式碼範例,FastAPI 將會

  • 驗證 GETPUT 請求的路徑中是否存在 item_id
  • 驗證 GETPUT 請求的 item_id 是否為 int 類型。
    • 如果不是,用戶端將會看到一個有用且清楚的錯誤訊息。
  • 檢查 GET 請求中是否存在名為 q 的選用查詢參數(例如 http://127.0.0.1:8000/items/foo?q=somequery)。
    • 由於 q 參數使用 = None 宣告,因此它是選用的。
    • 如果沒有 None,它將會是必需的(就像 PUT 中的主體一樣)。
  • 對於 /items/{item_id}PUT 請求,將主體作為 JSON 讀取
    • 檢查它是否具有必需的屬性 name,該屬性應為 str 類型。
    • 檢查它是否具有必需的屬性 price,該屬性必須為 float 類型。
    • 檢查它是否具有選用屬性 is_offer,如果存在,該屬性應為 bool 類型。
    • 所有這些也適用於深度嵌套的 JSON 物件。
  • 自動在 JSON 之間進行轉換。
  • 使用 OpenAPI 記錄所有內容,可供以下系統使用:
    • 互動式文件系統。
    • 自動產生多種語言的客戶端程式碼系統。
  • 直接提供 2 個互動式文件網頁介面。

我們只是略微介紹,但您應該已經了解它的運作方式。

嘗試將程式碼從

    return {"item_name": item.name, "item_id": item_id}

...從

        ... "item_name": item.name ...

...改成

        ... "item_price": item.price ...

...看看您的編輯器如何自動完成屬性並知道它們的類型

editor support

如需包含更多功能的完整範例,請參閱教學 - 使用者指南

搶先預告:教學 - 使用者指南包含

  • 從其他不同位置宣告參數,例如:標頭Cookie表單欄位檔案
  • 如何設定驗證限制,例如 maximum_lengthregex
  • 一個非常強大且易於使用的依賴注入系統。
  • 安全性與驗證,包含支援使用JWT 權杖OAuth2HTTP 基本驗證。
  • 更進階(但同樣簡單)的技巧,用於宣告深度巢狀的 JSON 模型(感謝 Pydantic)。
  • Strawberry 和其他函式庫整合GraphQL
  • 許多額外功能(感謝 Starlette),例如
    • WebSockets
    • 基於 HTTPX 和 pytest 的極簡測試
    • CORS
    • Cookie 工作階段
    • ...等等。

效能

獨立的 TechEmpower 基準測試顯示,在 Uvicorn 下執行的FastAPI 應用程式是目前最快的 Python 框架之一,僅次於 Starlette 和 Uvicorn 本身(FastAPI 內部使用)。 (*)

要了解更多資訊,請參閱基準測試章節。

依賴關係

FastAPI 依賴於 Pydantic 和 Starlette。

standard 依賴關係

當您使用 pip install "fastapi[standard]" 安裝 FastAPI 時,它會附帶 standard 群組的選用依賴關係

Pydantic 使用的

Starlette 使用的

  • httpx - 如果您想使用 TestClient,則需要此套件。
  • jinja2 - 如果您想使用預設範本設定,則需要此套件。
  • python-multipart - 如果您想使用 request.form() 支援表單"解析",則需要此套件。

FastAPI / Starlette 使用的

  • uvicorn - 用於載入和提供應用程式的伺服器。這包含 uvicorn[standard],其中包含一些高效能服務所需的依賴關係(例如 uvloop)。
  • fastapi-cli - 提供 fastapi 命令。

不含 standard 依賴關係

如果您不想包含 standard 選用依賴關係,則可以使用 pip install fastapi 而不是 pip install "fastapi[standard]" 進行安裝。

其他選用依賴關係

您可能需要安裝一些額外的依賴關係。

其他選用的 Pydantic 依賴關係

其他可選的 FastAPI 相依套件

  • 如果您想使用 ORJSONResponse,則需要 orjson
  • 如果您想使用 UJSONResponse,則需要 ujson

授權條款

本專案採用 MIT 授權條款。