From 0ea972723c41ad82b037902b65700f732e9ee9f3 Mon Sep 17 00:00:00 2001 From: Hendrik Makait Date: Mon, 22 May 2017 11:35:46 -0700 Subject: [PATCH] Auto-detect create_app() function in find_best_app() and call if it exists. --- flask/cli.py | 13 +++++++++++++ tests/test_cli.py | 27 +++++++++++++++++++++++++++ 2 files changed, 40 insertions(+) diff --git a/flask/cli.py b/flask/cli.py index 3d361be8..ad21d901 100644 --- a/flask/cli.py +++ b/flask/cli.py @@ -46,6 +46,19 @@ def find_best_app(module): if len(matches) == 1: return matches[0] + + # Search for app factory callable. + app_factory = getattr(module, 'create_app', None) + if app_factory is not None and callable(app_factory): + try: + app = app_factory() + if app is not None and isinstance(app, Flask): + return app + except TypeError: + raise NoAppException('Auto-detected a create_app() function in ' + 'module "%s", but could not call it without ' + 'specifying arguments.' % module.__name__) + raise NoAppException('Failed to find application in module "%s". Are ' 'you sure it contains a Flask application? Maybe ' 'you wrapped it in a WSGI middleware or you are ' diff --git a/tests/test_cli.py b/tests/test_cli.py index ab875cef..53c320eb 100644 --- a/tests/test_cli.py +++ b/tests/test_cli.py @@ -51,6 +51,27 @@ def test_find_best_app(test_apps): myapp = Flask('appname') assert find_best_app(Module) == Module.myapp + class Module: + @staticmethod + def create_app(): + return Flask('appname') + assert isinstance(find_best_app(Module), Flask) + assert find_best_app(Module).name == 'appname' + + class Module: + myapp = Flask('appname1') + @staticmethod + def create_app(): + return Flask('appname2') + assert find_best_app(Module) == Module.myapp + + class Module: + myapp = Flask('appname1') + @staticmethod + def create_app(foo): + return Flask('appname2') + assert find_best_app(Module) == Module.myapp + class Module: pass pytest.raises(NoAppException, find_best_app, Module) @@ -60,6 +81,12 @@ def test_find_best_app(test_apps): myapp2 = Flask('appname2') pytest.raises(NoAppException, find_best_app, Module) + class Module: + @staticmethod + def create_app(foo): + return Flask('appname2') + pytest.raises(NoAppException, find_best_app, Module) + def test_prepare_exec_for_file(test_apps): """Expect the correct path to be set and the correct module name to be returned.