Flask应用上下文与请求上下文深度剖析
请深入解释Flask的应用上下文(Application Context)和请求上下文(Request Context)的生命周期、内部实现(LocalStack/ LocalProxy)以及线程安全机制。
回答
屠龙少年
上下文类型:
- 应用上下文(
current_app、g):通过app.app_context()创建,在应用级操作(如Celery任务)中显式推送 - 请求上下文(
request、session):每次HTTP请求时自动推送,请求结束后自动弹出
内部实现:
Flask使用Werkzeug的LocalStack和LocalProxy实现线程隔离:
Local:类似threading.local(),每个线程独立存储LocalStack:线程隔离的栈结构,支持push()/pop()LocalProxy:代理对象,访问时自动从LocalStack栈顶获取真实对象
生命周期:
- 请求到达WSGI服务器
- Flask创建
Request对象,推入请求上下文栈 - 如果应用上下文栈为空,自动推入应用上下文
- 执行视图函数(通过
request、session、g等代理访问) - 生成响应
- 清理上下文(弹出请求上下文)
g对象:存储在应用上下文中,在一次请求中全局可访问,用于缓存数据库连接、用户信息等。请求结束后自动销毁。
线程安全:每个线程/协程有自己的LocalStack实例,上下文互不干扰。ASGI模式(Quart)使用contextvars替代LocalStack。