I am using the app factory pattern to set up my Flask application. My app uses the Flask-Babel extension, and that is set up in the factory as well. However, I want to access the extension in a blueprint in order to use it,
The factory is in __init__.py
.
def create_app(object_name):
app = Flask(__name__)
app.config.from_object(object_name)
babel = Babel(app)
app.register_blueprint(main_blueprint)
app.register_blueprint(category_blueprint)
app.register_blueprint(item_blueprint)
db.init_app(app)
return app
I want to add the following to main.py
:
@babel.localeselector
def get_locale():
if 'locale' in session:
return session['locale']
return request.accept_languages.best_match(LANGUAGES.keys())
@application.route('/locale/<locale>/', methods=['GET'])
def set_locale(locale):
session['locale'] = locale
redirect_to = request.args.get('redirect_to', '/')
return redirect(redirect_to) # Change this to previous url
Unfortunately, main.py
doesn't have access to the babel
variable from the application factory. How should I go about solving this?
Flask extensions are designed to be instantiated without an app instance for exactly this case. Outside the factory, define your extensions. Inside the factory, call init_app
to associate the app with the extension.
babel = Babel()
def create_app():
...
babel.init_app(app)
...
Now the babel
name is importable at any time, not just after the app has been created.
You already appear to be doing this correctly with the db
(Flask-SQLAlchemy) extension.
In the case of your specific babel.localeselector
example, it might make more sense to put that next to babel
since it's being defined there.