使用Flask工厂函数时如何定义before_request函数?
工厂函数模式下定义Flask before_request的正确姿势
嘿,这个问题我之前踩过坑!咱们先搞明白为啥会报“out of application context”错误:当你直接在工厂函数外面用@current_app.before_request装饰函数时,代码执行到这里的时候,create_app()还没运行,压根没创建Flask应用实例,current_app是依赖应用上下文才能存在的,这时候自然找不到对应的app,就报错了。
下面给你两种靠谱的解决方法:
方法1:在工厂函数内部直接注册before_request
既然工厂函数是创建app的地方,那咱们就在这里直接定义或者注册钩子函数,此时app实例已经存在,完全处于应用上下文里,不会有问题:
from flask import Flask, current_app def create_app(): app = Flask(__name__) # 方式A:在工厂函数内直接定义钩子 @app.before_request def before_req(): # 这里可以正常访问current_app或者直接用app变量 print(f"当前应用名称:{current_app.name}") # 比如做一些请求前的初始化操作,比如连接数据库、校验token等 pass # 方式B:如果钩子函数是外部定义的,用app.before_request注册它 # def external_before_request(): # print("外部定义的before_request钩子") # app.before_request(external_before_request) return app
方法2:用蓝图(Blueprint)组织钩子(适合代码拆分场景)
如果你的项目比较大,不想把所有钩子都堆在工厂函数里,可以用蓝图来管理,然后在工厂函数里注册蓝图即可:
from flask import Flask, Blueprint, current_app # 先创建一个蓝图 main_bp = Blueprint("main", __name__) # 在蓝图上定义before_request钩子 @main_bp.before_request def bp_before_request(): print(f"蓝图钩子触发,当前应用:{current_app.name}") # 同样可以做请求前的处理逻辑 pass def create_app(): app = Flask(__name__) # 把蓝图注册到app上 app.register_blueprint(main_bp) return app
这样拆分后,代码结构更清晰,蓝图的钩子会在蓝图注册后自动和app关联,完全不用担心上下文问题。
内容的提问来源于stack exchange,提问作者user11125012
相关产品推荐
相关产品推荐

