什麼是HTTP狀態碼?¶
HTTP狀態碼是服務器向客戶端返回的數字代碼,用於表示請求的處理結果。比如“200”表示請求成功,“404”表示請求的資源不存在。在FastAPI中,正確設置狀態碼能幫助API客戶端(如前端、其他服務)準確理解請求結果,是構建健壯API的基礎。
FastAPI中如何設置狀態碼?¶
FastAPI提供了兩種常用方式設置狀態碼:
1. 直接在路由函數返回時指定:通過元組 (數據, 狀態碼) 返回。
2. 使用HTTPException異常:拋出帶有狀態碼和錯誤信息的異常(推薦用於錯誤場景)。
示例代碼(兩種方式對比):
from fastapi import FastAPI, HTTPException
app = FastAPI()
# 方式1:直接返回元組
@app.get("/hello")
def say_hello():
return {"message": "Hello"}, 200 # 返回200 OK
# 方式2:拋出HTTPException(錯誤場景)
@app.get("/users/{user_id}")
def get_user(user_id: int):
if user_id != 1:
raise HTTPException(
status_code=404,
detail="User not found"
)
return {"user_id": user_id, "name": "Alice"}
常見狀態碼及使用場景¶
以下是初學者最常用的狀態碼,附簡單示例幫助理解:
1. 200 OK:請求成功¶
場景:GET/POST/PUT等請求處理成功時返回,返回具體數據或結果。
示例:查詢存在的用戶信息:
fake_users_db = {1: {"name": "Alice"}, 2: {"name": "Bob"}}
@app.get("/users/{user_id}")
def get_user(user_id: int):
if user_id in fake_users_db:
return fake_users_db[user_id] # 自動返回200 OK
raise HTTPException(status_code=404, detail="User not found") # 不存在返回404
2. 404 Not Found:資源不存在¶
場景:請求的資源(如ID、路徑)不存在時返回,常見於GET/DELETE請求找不到目標。
示例:請求不存在的用戶ID:
@app.get("/users/{user_id}")
def get_user(user_id: int):
if user_id not in fake_users_db:
return {"error": "User not found"}, 404 # 返回404
return fake_users_db[user_id]
3. 500 Internal Server Error:服務器內部錯誤¶
場景:服務器代碼出錯、數據庫連接失敗等服務器端問題時返回(儘量避免暴露給用戶,應捕獲異常返回友好提示)。
錯誤示例(避免):
@app.get("/crash")
def crash():
1 / 0 # 故意製造錯誤,FastAPI默認返回500(但實際應捕獲!)
正確處理:用try-except捕獲並返回400等具體錯誤:
from fastapi import HTTPException
@app.get("/divide")
def divide(a: float, b: float):
try:
return a / b
except ZeroDivisionError:
raise HTTPException(status_code=400, detail="除數不能爲0")
4. 201 Created:資源創建成功¶
場景:POST請求創建新資源(如新增用戶、商品)成功時返回,需返回新資源的信息。
示例:創建新用戶:
@app.post("/users")
def create_user(new_user: dict): # 假設接收新用戶數據
new_id = 3 # 數據庫新增ID
created_user = {"id": new_id, **new_user}
return created_user, 201 # 返回201和創建的用戶
5. 204 No Content:無內容返回¶
場景:DELETE/PUT請求成功但無需返回數據(如刪除資源後),僅返回狀態碼。
示例:刪除用戶:
from fastapi import status
@app.delete("/users/{user_id}")
def delete_user(user_id: int):
if user_id in fake_users_db:
del fake_users_db[user_id]
return {"message": "User deleted"}, status.HTTP_204_NO_CONTENT # 204無內容
raise HTTPException(status_code=404, detail="User not found")
6. 400 Bad Request:請求參數錯誤¶
場景:請求參數不合法(如必填字段缺失、格式錯誤)時返回。
示例:提交負數價格(Pydantic模型驗證):
from pydantic import BaseModel
class Item(BaseModel):
name: str
price: float
@app.post("/items")
def create_item(item: Item):
if item.price < 0:
raise HTTPException(status_code=400, detail="價格不能爲負數")
return item, 201
7. 401 Unauthorized / 403 Forbidden¶
- 401:未認證(用戶未登錄)。
示例:訪問需登錄的接口:
from fastapi import Depends, HTTPException
from fastapi.security import OAuth2PasswordBearer
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="token")
async def get_current_user(token: str = Depends(oauth2_scheme)):
if not token: # 假設token不存在則未認證
raise HTTPException(status_code=401, detail="未認證")
@app.get("/profile")
def get_profile(user=Depends(get_current_user)):
return {"message": "已登錄"}
- 403:已認證但權限不足(如普通用戶訪問管理員接口)。
示例:普通用戶訪問管理員接口:
async def get_admin_role(user: dict = Depends(get_current_user)):
if user.get("role") != "admin":
raise HTTPException(status_code=403, detail="權限不足")
@app.get("/admin")
def admin_route(user=Depends(get_admin_role)):
return {"message": "管理員數據"}
最佳實踐:不同HTTP方法的狀態碼習慣¶
- GET:查詢數據,成功返回200,失敗返回404(資源不存在)或400(參數錯誤)。
- POST:創建資源,成功返回201,參數錯誤返回400。
- PUT/PATCH:更新資源,成功返回200或204,失敗返回400/404。
- DELETE:刪除資源,成功返回204,失敗返回404。
總結¶
狀態碼是API的“語言”,正確使用能讓客戶端清晰理解請求結果。FastAPI通過status_code參數和HTTPException簡化了狀態碼設置,初學者需重點掌握200(成功)、404(資源不存在)、500(服務器錯誤)、201(創建成功)、400(參數錯誤)等核心狀態碼的場景,避免因狀態碼混亂導致前端或下游服務錯誤。
(注:FastAPI自動生成的Swagger文檔會顯示路由的狀態碼,調試時可通過文檔直觀查看各接口的狀態碼定義。)