FastAPI中为APIRouter统一配置请求命名依赖的方法
FastAPI路由全局统一配置请求体与依赖注入实现
需求说明
开发FastAPI服务时,某APIRouter下的所有端点接收相同结构的请求体,希望在Router层面统一配置,避免每个端点函数重复声明请求对象和参数:
- 请求体包含业务参数
num1、num2,以及请求版本、发送方等元信息 - 需将
num1、num2作为独立变量使用,元信息存入requests_info字段 - 所有端点无需重复声明
request: Request即可访问请求对象
解决方案:类依赖+路由全局注入
通过FastAPI的类依赖封装请求处理逻辑,再在APIRouter中全局注入该依赖,实现所有端点共享配置。
步骤1:定义请求体模型
用Pydantic模型描述完整请求体结构,包含业务参数和元信息:
from pydantic import BaseModel class CalculatorRequest(BaseModel): num1: int num2: int version: str sender: str # 可根据需求添加其他元信息字段
步骤2:创建类依赖
封装请求解析逻辑,自动提取业务参数、元信息并保留原始Request对象:
from fastapi import Request class RequestContext: def __init__(self, request: Request, body: CalculatorRequest): self.request = request # 原始Request对象,无需重复声明 self.num1 = body.num1 self.num2 = body.num2 # 过滤业务参数,仅保留元信息存入requests_info self.requests_info = {k: v for k, v in body.dict().items() if k not in ["num1", "num2"]}
步骤3:路由全局注入依赖
在APIRouter初始化时配置dependencies参数,让所有端点自动加载该依赖:
from fastapi import APIRouter, Depends router = APIRouter(dependencies=[Depends(RequestContext)])
步骤4:编写端点函数
每个端点只需声明依赖实例即可访问所有所需变量,无需重复配置:
@router.post("/add") async def add(ctx: RequestContext = Depends()) -> int: # 直接使用ctx.requests_info、ctx.request、ctx.num1、ctx.num2 print("请求元信息:", ctx.requests_info) return ctx.num1 + ctx.num2 @router.post("/multiply") async def multiply(ctx: RequestContext = Depends()) -> int: print("请求元信息:", ctx.requests_info) return ctx.num1 * ctx.num2 @router.post("/subtract") def subtract(ctx: RequestContext = Depends()) -> int: print("请求元信息:", ctx.requests_info) return ctx.num1 - ctx.num2
完整修改后的calculator.py代码
from fastapi import APIRouter, Depends, Request from pydantic import BaseModel # 定义完整请求体模型 class CalculatorRequest(BaseModel): num1: int num2: int version: str sender: str # 类依赖:统一处理请求上下文 class RequestContext: def __init__(self, request: Request, body: CalculatorRequest): self.request = request self.num1 = body.num1 self.num2 = body.num2 self.requests_info = {k: v for k, v in body.dict().items() if k not in ["num1", "num2"]} # 全局注入依赖的路由 router = APIRouter(dependencies=[Depends(RequestContext)]) @router.post("/add") async def add(ctx: RequestContext = Depends()) -> int: print("请求元信息:", ctx.requests_info) return ctx.num1 + ctx.num2 @router.post("/multiply") async def multiply(ctx: RequestContext = Depends()) -> int: print("请求元信息:", ctx.requests_info) return ctx.num1 * ctx.num2 @router.post("/subtract") def subtract(ctx: RequestContext = Depends()) -> int: print("请求元信息:", ctx.requests_info) return ctx.num1 - ctx.num2
说明
- 类依赖
RequestContext会自动解析请求体并封装所有所需数据,避免每个端点重复编写解析逻辑 - 路由全局注入后,所有端点只需通过
ctx: RequestContext = Depends()即可获取统一的请求上下文 - 原始
Request对象被保留在ctx.request中,如需操作请求头、客户端信息等可直接使用
内容的提问来源于stack exchange,提问作者Pranjal Doshi
相关产品推荐
相关产品推荐

