FastAPI

Python 现代 API 框架 - 类型提示自动生成文档和验证,原生异步,媲美 Node/Go 的速度

TL;DR

一句话:FastAPI 是 Python 构建 API 的利器——类型提示变成文档、验证和速度。

核心优势

  • 自动生成文档 - Swagger UI 和 ReDoc 免费送
  • 类型驱动 - Pydantic 从类型提示自动验证
  • 原生异步 - 基于 Starlette,快如 Node/Go
  • 开发友好 - 极佳的编辑器支持和错误提示

Core Concepts

概念 1:类型提示 = 验证 + 文档

类型提示自动变成请求验证、API 文档和编辑器自动补全。

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()

class User(BaseModel):
    name: str
    email: str
    age: int | None = None

@app.post("/users/")
def create_user(user: User):  # 自动验证
    return user  # 自动序列化

概念 2:路径操作

装饰器定义 HTTP 端点:

@app.get("/users/{user_id}")    # GET 带路径参数
@app.post("/users/")            # POST
@app.put("/users/{user_id}")    # PUT
@app.delete("/users/{user_id}") # DELETE

概念 3:依赖注入

可复用的依赖,用于认证、数据库连接等。

from fastapi import Depends

def get_current_user(token: str = Header()):
    return decode_token(token)

@app.get("/me")
def read_me(user = Depends(get_current_user)):
    return user

Quick Start

安装

pip install "fastapi[standard]"

创建 main.py

from fastapi import FastAPI

app = FastAPI()

@app.get("/")
def root():
    return {"message": "Hello FastAPI!"}

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

运行

fastapi dev main.py
# 打开 http://localhost:8000
# 文档在 http://localhost:8000/docs

Gotchas

路由顺序很重要

# ❌ 错误 - /users/me 永远匹配不到
@app.get("/users/{user_id}")
def get_user(user_id: str): ...

@app.get("/users/me")  # 永远到不了!
def get_me(): ...

# ✅ 正确 - 具体路由放前面
@app.get("/users/me")
def get_me(): ...

@app.get("/users/{user_id}")
def get_user(user_id: str): ...

async vs sync 函数

# I/O 操作用 async
@app.get("/async")
async def async_endpoint():
    data = await fetch_from_db()  # 非阻塞
    return data

# CPU 密集或阻塞调用用 sync
@app.get("/sync")
def sync_endpoint():
    return heavy_computation()  # 在线程池运行

请求体需要 Pydantic 模型

from pydantic import BaseModel

class Item(BaseModel):
    name: str
    price: float
    description: str | None = None

@app.post("/items/")
def create_item(item: Item):  # 请求体自动验证
    return item

# 获取原始 body
from fastapi import Request
@app.post("/raw")
async def raw_body(request: Request):
    body = await request.body()

查询参数 vs 路径参数

# 路径参数:URL 的一部分,必需
@app.get("/users/{user_id}")  # /users/123
def get_user(user_id: int): ...

# 查询参数:? 后面,默认可选
@app.get("/items/")  # /items/?skip=0&limit=10
def get_items(skip: int = 0, limit: int = 10): ...

When to Use

适合

  • REST API 和微服务
  • ML 模型服务
  • 实时应用(WebSockets)
  • 喜欢类型安全的团队

不适合

  • 带模板的全栈应用(用 Django)
  • 简单脚本(杀鸡用牛刀)
  • Python 2 遗留项目

对比

特性FastAPIDjangoFlask
速度非常快中等中等
异步原生有限有限
自动文档
学习曲线简单中等简单

Next Steps

Cheatsheet

模式代码
路径参数@app.get("/items/{id}")
查询参数def f(skip: int = 0)
请求体def f(item: Item)
请求头def f(token: str = Header())
Cookiedef f(session: str = Cookie())
响应模型@app.get("/", response_model=Item)
状态码@app.post("/", status_code=201)
依赖def f(db = Depends(get_db))
后台任务background_tasks.add_task(fn, arg)