首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >烧瓶AttributeError:模块对象没有属性'app‘

烧瓶AttributeError:模块对象没有属性'app‘
EN

Stack Overflow用户
提问于 2019-04-16 12:33:36
回答 1查看 6.7K关注 0票数 2

我是一个新的酒瓶,我有下面的导入相关的AttributeError时,flask run在flask_lab文件夹。

任何帮助都将不胜感激。

工作目录:

代码语言:javascript
复制
flask_lab
├── __init__.py
├── Pipfile
├── Pipfile.lock
├── README.md
├── tmp
│   ├── __init__.py
│   └── test.py
└── app.py

flask_lab/app.py:

代码语言:javascript
复制
import os
import click

from flask import Flask
from flask_sqlalchemy import SQLAlchemy

import flask_lab.tmp.test.demo

app = Flask(__name__)
prefix = 'sqlite:////'
app.config['SQLALCHEMY_DATABASE_URI'] = prefix + os.path.join(app.root_path, 'data.db')
db = SQLAlchemy(app)

class User(db.Model): 
    id = db.Column(db.Integer, primary_key=True) 
    name = db.Column(db.String(20))

flask_lab.tmp.test.demo()

flask_lab/tmp/test.py:

代码语言:javascript
复制
import flask_lab.app

print(flask_lab.app.db)


def demo():
    print('yeah!')

错误:

代码语言:javascript
复制
Traceback (most recent call last):
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/bin/flask", line 10, in <module>
    sys.exit(main())
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 894, in main
    cli.main(args=args, prog_name=name)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 557, in main
    return super(FlaskGroup, self).main(*args, **kwargs)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/core.py", line 717, in main
    rv = self.invoke(ctx)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/core.py", line 1137, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/core.py", line 956, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/core.py", line 555, in invoke
    return callback(*args, **kwargs)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/decorators.py", line 64, in new_func
    return ctx.invoke(f, obj, *args, **kwargs)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/click/core.py", line 555, in invoke
    return callback(*args, **kwargs)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 767, in run_command
    app = DispatchingApp(info.load_app, use_eager_loading=eager_loading)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 293, in __init__
    self._load_unlocked()
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 317, in _load_unlocked
    self._app = rv = self.loader()
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 377, in load_app
    raise_if_not_found=False)
  File "/home/huafeng/.local/share/virtualenvs/flask_lab-x_qc9OjH/lib/python3.6/site-packages/flask/cli.py", line 235, in locate_app
    __import__(module_name)
  File "/home/huafeng/Desktop/flask_lab/app.py", line 7, in <module>
    import flask_lab.tmp.test.demo
  File "/home/huafeng/Desktop/flask_lab/tmp/test.py", line 3, in <module>
    print(flask_lab.app.db)
AttributeError: module 'flask_lab' has no attribute 'app'

有人抱怨堆叠过多的代码和不够的细节.更多的话,更多的话..。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-04-16 13:08:21

在解释app.py时,如果python解释器遇到一行import flask_lab.tmp.test.demo,那么它将立即开始解释tmp/test.py。但是tmp/test.py再次导入flask_lab。

此时,由于解释器已经遇到flask_lab,它将开始在该命名空间中搜索app。但直到那条线才到达。由于在模块中定义tmp.test之前已经导入了app,所以还没有flask_lab.app,因此出现了错误。

如果您直接调用了tmp.test,那么您也会遇到一个循环导入错误。

因此,出路是避免循环导入场景。将db对象移动到单独的模块,并在这两个模块中调用它。烧瓶-SQLAlchemy提供了一个名为init_app的方法,用于这种用例。

让我们创建一个名为公共的模块,它将包含公共变量。

烧瓶实验室/公共实验室

代码语言:javascript
复制
from flask_sqlalchemy import SQLAlchemy
db = SQLAlchemy()

烧瓶实验室/app.py:

代码语言:javascript
复制
import os
import click

from flask import Flask
from .common import db
from .tmp.test import demo

class User(db.Model): 
    id = db.Column(db.Integer, primary_key=True) 
    name = db.Column(db.String(20))

app = Flask(__name__)
prefix = 'sqlite:////'
app.config['SQLALCHEMY_DATABASE_URI'] = prefix + os.path.join(app.root_path, 'data.db')
db.init_app(app)

demo()

烧瓶实验室/tmp/test.py:

代码语言:javascript
复制
from .common import db

print(db)


def demo():
    print('yeah!')

请注意,我还将flask_lab导入替换为相对导入。它们更干净。包内的代码应避免在导入中使用包名。这样,如果稍后更改包名,就可以这样做,而不必更改内部的所有代码。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55708257

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档