简体   繁体   English

如何根据我的项目结构访问应用程序上下文之外的烧瓶配置变量?

[英]How to access flask config variables outside application context according to my project structure?

spinngod.py - flask app starter code spinngod.py -flask 应用程序启动代码

from app import create_app
import sys

run_profile = str(sys.argv[1]) if len(sys.argv) >= 2 else 'development'
app = create_app(run_profile)

print("App Root Path:" + app.root_path)

if __name__ == '__main__':
    print sys.path
    app.run(debug=True, host='0.0.0.0')

app/ init .py - creates flask app app/ init .py - 创建烧瓶应用

def create_app(profile_name):
    print "currently active profile:" + profile_name
    app = Flask(__name__)

    ############# configurations ####################
    app.config.from_object(config[profile_name])
    configure_app(app)
    configure_app_logger(app)

    #################### blueprint registration and rest_plus namespace additions ###############
    from api_1_0 import api as api_1_0_blueprint
    from api_1_0.restplus import api_restplus

    # ************************************************** #
    api_restplus.init_app(api_1_0_blueprint)
    api_restplus.add_namespace(application_namespace)
    api_restplus.add_namespace(pipeline_template_namespace)
    api_restplus.add_namespace(loadbalancer_namespace)
    api_restplus.add_namespace(servergroup_namespace)
    api_restplus.add_namespace(task_namespace)
    # ************************************************** #

    app.register_blueprint(api_1_0_blueprint)

    ##############################################################
    return app

I want to access flask config variables defined in config.py in some other files which are outside application context.我想在应用程序上下文之外的其他一些文件中访问 c​​onfig.py 中定义的烧瓶配置变量。 The app configuration depends on which profile it is started with (dev,stage or production) which is being passed from command line as an arg.应用程序配置取决于从命令行作为参数传递的配置文件(开发、阶段或生产)。

The only way that I can think of accessing config variables outside app context is to set profile (dev,stage or prod) as an environment variable and then import directly from config file.我能想到在应用程序上下文之外访问配置变量的唯一方法是将配置文件(dev、stage 或 prod)设置为环境变量,然后直接从配置文件导入。

The second way that I tried was to move creation of flask app in app/ init .py outside method.我尝试的第二种方法是在 app/ init .py 外部方法中移动烧瓶应用程序的创建。

This is how I am trying to access config variables in another class.这就是我尝试访问另一个类中的配置变量的方式。

import requests


class Client(object):
    def __init__(self):
        from app import app
        print "fjaijflkajsf" + app.config['SPINNAKER_BASE_URL']
        pass

Is there a way better of doing this in flask ?有没有更好的方法在烧瓶中做到这一点?

From the docs :文档

Rather than passing the application around to each function, the current_app and g proxies are accessed instead.不是将应用程序传递给每个函数,而是访问 current_app 和 g 代理。

The Flask application object has attributes, such as config, that are useful to access within views and CLI commands. Flask 应用程序对象具有可用于在视图和 CLI 命令中访问的属性,例如 config。 However, importing the app instance within the modules in your project is prone to circular import issues.但是,在项目的模块中导入应用程序实例很容易出现循环导入问题。

Flask solves this issue with the application context. Flask 通过应用程序上下文解决了这个问题。 Rather than referring to an app directly, you use the the current_app proxy, which points to the application handling the current activity.不是直接引用应用程序,而是使用 current_app 代理,它指向处理当前活动的应用程序。

You import current_app like this:你像这样导入 current_app :

from flask import current_app

and then access the config or other attributes like this:然后像这样访问配置或其他属性:

config = current_app.config

Example:例子:

src/application.py (where config is set in the context) src/application.py(其中 config 在上下文中设置)

create_app():
  app = Flask('app')
  app.config.from_object(some_class)
  return app

src/module/another_module.py src/module/another_module.py

from flask import current_app

def function_that_requires_config():
    config = current_app.config

Alternative:选择:

src/application.py (where config is set in the context) src/application.py(其中 config 在上下文中设置)

APP = create_app(os.environ.get('FLASK_ENV'))

src/module/another_module.py src/module/another_module.py

from src.application import APP

def function_that_requires_config():
   config_value = APP.config.get(config_key, default_value)

Not sure if it is good to put it here as it may not respond to the question directly, but here is the cleanest way i've figured to use config values outside of requests, without having to pass config as a param.不确定把它放在这里是否好,因为它可能不会直接回答问题,但这是我认为在请求之外使用配置值的最干净的方式,而不必将配置作为参数传递。

The solution is actually pretty simple, juste consider the part of your code as a flask_extension.解决方案实际上非常简单,只需将您的代码部分视为flask_extension。 my exemple will be the use of external api, with ROOT_URL in the config file, and i don't want to make api call from within my routes, so the api is in its own module.我的例子是使用外部 api,在配置文件中带有 ROOT_URL,我不想从我的路由中进行 api 调用,所以 api 在它自己的模块中。

in my create_app fuction:在我的 create_app 功能中:


from flask import Flask

from .api import api
from .configmodule import Config
from .model import db

def create_app(environment):
    app = Flask(__name__)
    app.config.from_object(Config.get_config(environment))
    db.init_app(app)
    api.init_app(app) # here i use api.init_app the same way i do for sqlalchemy

and in api/ init .py并在 api/ init .py

class Api:
    def init_app(self, app):
        self.config = app.config


api = Api()

and in any files in my api modude i can now write在我的 api 模块中的任何文件中,我现在可以编写

from . import api

def foo():
   print(api.config.get("API_ROOT_URL"))

this can even be improved if you feel the need to access some other global app vars from your module.如果您觉得需要从您的模块访问一些其他全局应用程序变量,这甚至可以改进。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM