在运行烧瓶应用程序后调用函数的正确方法是什么?

问题描述 投票:29回答:3

我对如何做一些我认为非常简单的事情感到有些困惑。我有一个使用Flask编写的简单应用程序。它看起来像这样:

from flask import Flask

app = Flask(__name__)

def _run_on_start(a_string):
    print "doing something important with %s" % a_string

@app.route('/')
def root():
    return 'hello world'

if __name__ == "__main__":
    if len(sys.argv) < 2:
        raise Exception("Must provide domain for application execution.")
    else:
        DOM = sys.argv[1]
        _run_on_start("%s" % DOM)
        app.run(debug=True)

我发现我的终端输出的是_run_on_start中的print语句,而不是其他常用的Flask app调试代码。如果我在app.run之前删除了调用,则输出正常。此外,我发现_run_on_start的输出在启动时重复两次,但我不知道它是否是一些奇怪的输出或者该函数实际上被调用了两次。

我假设这不是在调用app.run之前添加函数调用的正确方法。我查看了Flask文档并发现了可以使用的各种装饰器的提及,它允许您在某些请求之前/之后执行一个函数,但我想在运行app服务器时执行调用。

此外,我意识到,如果我从另一个模块调用此模块,即,不是当__name__ != "__main__"我不会接到_run_on_start的电话。

这里有什么正确的方法?在这两种情况下,当我从CL和另一个模块开始?

python web-frameworks flask werkzeug
3个回答
13
投票

重新加载器可以解释函数的重复输出。它首先要做的是在新线程中启动main函数,以便它可以监视源文件并在更改时重新启动线程。使用use_reloader=False选项禁用此选项。

如果您希望能够在从其他模块启动服务器时运行您的功能,请将其包装在一个函数中,并从另一个模块调用该函数:

def run_server(dom):
        _run_on_start("%s" % dom)
        app.run(debug=True, use_reloader=False)

if __name__ == '__main__':
    if len(sys.argv) < 2:
        raise Exception("Must provide domain for application execution.")
    else:
        DOM = sys.argv[1]
        run_server(DOM)

“正确的方法”取决于你真正想要在这里完成的事情。内置服务器用于在将应用程序部署到生产服务器之前在本地测试环境中运行应用程序,因此从不同模块启动它的问题本身并没有多大意义。


47
投票

可能你正在寻找Flask.before_first_request装饰,如:

@app.before_first_request
def _run_on_start(a_string):
    print "doing something important with %s" % a_string

0
投票
from flask import Flask

def create_app():
    app = Flask(__name__)
    def run_on_start(*args, **argv):
        print "function before start"
    run_on_start()
    return app

app = create_app()

@app.route("/")
def hello():
    return "Hello World!"
© www.soinside.com 2019 - 2024. All rights reserved.