FastAPI 處理靜態檔案 (Static Files)

如果你的 API 需要提供圖片、CSS、JavaScript 檔案,或是你要部署一個編譯好的前端專案 (如 React / Vue 的 dist 目錄),你需要使用 StaticFiles

掛載 StaticFiles

你需要使用 app.mount() 方法將 StaticFiles 應用程式掛載到指定的路徑上。

from fastapi import FastAPI
from fastapi.staticfiles import StaticFiles

app = FastAPI()

# 將 "static" 目錄掛載到 "/static" 路徑下
app.mount("/static", StaticFiles(directory="static"), name="static")

參數說明

  • "/static":URL 的前綴路徑。這代表所有以 /static 開頭的請求都會被導向這裡。
  • StaticFiles(directory="static")
    • directory="static":你的專案中存放靜態檔案的資料夾名稱。
  • name="static":這是給 FastAPI 內部使用的名稱,讓你可以用 url_for 來反查 URL。

使用方式

假設你的專案結構如下:

.
├── main.py
└── static
    ├── images
    │   └── logo.png
    └── styles.css

當你啟動伺服器後,你可以透過以下 URL 存取檔案:

  • http://127.0.0.1:8000/static/images/logo.png
  • http://127.0.0.1:8000/static/styles.css

用於 Single Page Application (SPA)

如果你是前後端分離,通常前端會 build 出一堆靜態檔案 (index.html, js, css)。

你可以將這些檔案放在一個資料夾 (例如 dist),然後掛載到根目錄 / (要小心不要覆蓋 API 路由) 或是特定目錄。

但要注意,SPA 通常需要處理「前端路由」的問題 (即隨便打一個網址都要回傳 index.html)。這通常需要自定義一個 Catch-all 的路由來回傳 FileResponse('dist/index.html')

from fastapi.responses import FileResponse

# ... API 路由定義 ...

# 處理 SPA 的前端路由 (放在最後面)
@app.get("/{full_path:path}")
async def serve_spa(full_path: str):
    return FileResponse("dist/index.html")

總結

  • 使用 mountStaticFiles 來提供靜態資源。
  • 記得安裝 aiofiles
  • 這使得 FastAPI 也可以作為一個簡單的 Web Server 使用。