烧瓶循环导入问题-从__init__.py将变量导入视图

时间:2019-08-29 11:25:12

标签: python flask python-import importerror

这是我的项目结构

myproject
    myproject
        __init__.py
        static
        templates
        views
            __init.py__
            home.py
    venv
    myproject.wsgi
    requirements.txt
    setup.py

这是我的 __init__.py

from flask import Flask, request, Response, render_template
from myproject.views import home

app = Flask(__name__, static_folder="static", static_url_path='/static')
test_string = "Hello World!"

app.register_blueprint(home.home)

这是我的 views/home.py

from flask import Flask, request, Response, Blueprint
import json
import requests
from myproject import test_string

home = Blueprint('home', __name__)

@home.route('/', methods=['GET'])
def test():
    return(test_string)

当我访问页面时,出现错误ImportError: cannot import name test_string。 Python导入系统确实令人困惑,我不确定在这里做错了什么,但是我怀疑这是一个循环导入问题。

我该如何解决?

1 个答案:

答案 0 :(得分:1)

尝试将__init__.py行中的from myproject.views import home行移动到test_string = "Hello World!"之后。

这样,Python将找到test_string名称。

要了解循环导入,您必须“像解释器一样思考”,当您执行__init__.py时,解释器将:

  1. 执行__init__.py的第1行
  2. 执行该行所隐含的所有代码(从flask导入内容)
  3. 执行__init__.py的第2行
  4. 执行views/home.py的第1行(仅从烧瓶中导入Blueprint,因为这是唯一尚未导入的内容)
  5. 执行views/home.py的第2 + 3行(导入json和请求)
  6. 执行views/home.py的第4行
  7. 回到__init__.py中的他执行了什么并搜索名称test_string

在这里引发错误,因为他执行的事情不理解test_string。如果您在执行test_string = "Hello World!"之后将导入 后移,解释器将在名称空间中找到该名称。

这通常被认为是错误的设计,恕我直言,存储test_string的最佳位置是一个config.py文件,该文件中不会从其他项目模块执行任何导入,从而避免了循环导入。