python flask 使用 Blueprint 配合 current_app 發生錯誤 RuntimeError: Working outside of application context.?
在 Flask 中,當你在 Blueprint 中使用 current_app 時,必須確保 Flask 應用程式的 應用上下文 (application context) 是活動狀態的,否則會遇到 "RuntimeError: Working outside of application context" 錯誤。
錯誤原因
current_app 依賴於 Flask 的 應用上下文,但 Blueprint 是獨立於應用程式的。當你嘗試在 Blueprint 外部(例如模組級別)直接使用 current_app,或是在沒有開啟應用上下文的情況下使用它,就會導致錯誤。
解決方案
1. 使用 with app.app_context() 確保有應用上下文
在非請求處理(如初始化時)使用 app.app_context() 來確保 current_app 可以正常運作。
from flask import Flask, Blueprint, current_app bp = Blueprint("example", __name__) @bp.route("/") def index(): return f"App name: {current_app.name}" # 這裡可以使用 current_app,因為請求處理期間 Flask 會自動提供應用上下文 def print_app_name(): with current_app.app_context(): # 確保應用上下文有效 print(current_app.name) app = Flask(__name__) app.register_blueprint(bp) with app.app_context(): # 在 Blueprint 外部使用 current_app 需要手動開啟應用上下文 print(current_app.name)
2. 使用 flask.current_app 只在請求期間存取
如果 current_app 是在請求處理函式內使用的,那麼不需要手動處理應用上下文,因為 Flask 會自動提供它。
@bp.route("/config") def get_config(): return current_app.config["DEBUG"] # 這裡可以安全地使用 current_app
3. 在 Blueprint 模組內避免全域變數存取 current_app
如果 current_app 是在 Blueprint 外部(模組級別)使用的,應該改用 Flask 應用程式的 app.config,或者使用函數來動態存取 current_app。
錯誤範例(不應該在 Blueprint 頂部存取 current_app)
from flask import current_app # X 這會導致錯誤,因為 current_app 只能在應用上下文中存取 db_uri = current_app.config["SQLALCHEMY_DATABASE_URI"]
正確作法
def get_db_uri(): return current_app.config["SQLALCHEMY_DATABASE_URI"] @bp.route("/db") def show_db_uri(): return get_db_uri()
4. 改用 app.config 來存取設定
如果你需要在 Blueprint 外部的模組級別存取設定,建議直接從 Flask 應用程式的 app.config 來取得。
def create_app(): app = Flask(__name__) app.config["MY_SETTING"] = "Hello, Flask!" app.register_blueprint(bp) return app def some_function(): from flask import current_app with current_app.app_context(): print(current_app.config["MY_SETTING"])
結論
current_app 只能在 Flask 應用上下文內 存取。
解決方法
在非請求處理代碼中,使用 with app.app_context() 來開啟應用上下文。
只在請求期間使用 current_app,因為 Flask 會自動提供應用上下文。
避免在 Blueprint 模組級別存取 current_app,應該改用函數來動態取得設定值。
在應用初始化時,建議直接使用 app.config 來存取設定。
這樣可以避免 "RuntimeError: Working outside of application context" 錯誤。
留言板
歡迎留下建議與分享!希望一起交流!感恩!