-
Bjarke Madsen authoredBjarke Madsen authored
__init__.py 3.47 KiB
"""
automatically invoked app factory
"""
import logging
import os
import pkg_resources
import sentry_sdk
from sentry_sdk.integrations.flask import FlaskIntegration
from flask import Flask
from flask_cors import CORS # for debugging
# the currently available stubs for flask_migrate are old (they depend on sqlalchemy 1.4 types)
from flask_migrate import Migrate, upgrade # type: ignore
from flask_login import LoginManager # type: ignore
from compendium_v2 import config, environment
from compendium_v2.db import db
from compendium_v2.auth import setup_oauth
from compendium_v2.auth.session_management import setup_login_manager
sentry_dsn = os.getenv('SENTRY_DSN')
if sentry_dsn:
sentry_sdk.init(
dsn=sentry_dsn,
integrations=[FlaskIntegration()],
release=pkg_resources.get_distribution('compendium-v2').version)
environment.setup_logging()
logger = logging.getLogger(__name__)
def _create_app() -> Flask:
# used by sphinx to create documentation without config and db migrations
app = Flask(__name__)
CORS(app)
from compendium_v2.routes import default
app.register_blueprint(default.routes, url_prefix='/')
from compendium_v2.routes import authentication
app.register_blueprint(authentication.routes, url_prefix='/')
from compendium_v2.routes import api
app.register_blueprint(api.routes, url_prefix='/api')
return app
def _create_app_with_db(app_config) -> Flask:
# used by the tests and the publishers
app = _create_app()
app.config['SECRET_KEY'] = app_config['SECRET_KEY']
app.config['SESSION_COOKIE_SECURE'] = True
if 'oidc' not in app_config:
app.config['LOGIN_DISABLED'] = True
logger.info('No OIDC configuration found, authentication disabled')
else:
logger.info('OIDC configuration found, authentication will be enabled')
app.config['SQLALCHEMY_DATABASE_URI'] = app_config['SQLALCHEMY_DATABASE_URI']
if 'SQLALCHEMY_BINDS' in app_config:
# for the publishers
app.config['SQLALCHEMY_BINDS'] = app_config['SQLALCHEMY_BINDS']
if 'mail' in app_config:
mail_config = app_config['mail']
app.config['MAIL_ENABLE'] = True
app.config['MAIL_SERVER'] = mail_config['MAIL_SERVER']
app.config['MAIL_PORT'] = mail_config['MAIL_PORT']
app.config['MAIL_SENDER_EMAIL'] = mail_config['MAIL_SENDER_EMAIL'] # email address to send emails from
excluded_admins = mail_config.get('MAIL_EXCLUDED_ADMINS', [])
app.config['MAIL_EXCLUDED_ADMINS'] = excluded_admins # list of admin emails not to send emails to
else:
app.config['MAIL_ENABLE'] = False
db.init_app(app)
return app
def create_app() -> Flask:
"""
overrides default settings with those found
in the file read from env var SETTINGS_FILENAME
:return: a new flask app instance
"""
assert 'SETTINGS_FILENAME' in os.environ, "environment variable 'SETTINGS_FILENAME' is required"
with open(os.environ['SETTINGS_FILENAME']) as f:
app_config = config.load(f)
app = _create_app_with_db(app_config)
Migrate(app, db, directory=os.path.join(os.path.dirname(__file__), 'migrations'))
logging.info('Flask app initialized')
login_manager = LoginManager()
login_manager.init_app(app)
login_manager.login_view = 'authentication.login'
setup_login_manager(login_manager)
setup_oauth(app, app_config.get('oidc'))
# run migrations on startup
with app.app_context():
upgrade()
return app