flask - blueprint - sqlalchemy - cannot import name 'db' into moles file
Asked Answered
W

1

16

I'm new in bluprint, and have problem with importing db into mydatabase.py file which is models file.

I've faced with this error:

ImportError: cannot import name 'db'

The tree of my project

nikoofar/
    run.py
    bookshelf/
        __init__.py
        mydatabase.py
        main/
            controllers.py
            __init__.py

run.py

from bookshelf import app

if __name__ == '__main__':
    app.run(debug=True, port=8000)

bookshelf / intit.py

from flask import Flask
from bookshelf.main.controllers import main
from flask_sqlalchemy import SQLAlchemy
from mydatabase import pmenu


app = Flask(__name__, instance_relative_config=True)
db = SQLAlchemy(app)
db.init_app(app)
application.config['SQLALCHEMY_DATABASE_URI'] = 'mysql+pymysql://username:password@localhost/databasename'

app.config.from_object('config')

app.register_blueprint(main, url_prefix='/')

bookshelf / main / controllers.py

from flask import Blueprint
from bookshelf.mydatabase import *
from flask_sqlalchemy import SQLAlchemy


main = Blueprint('main', __name__)


@main.route('/')
def index():
    g = pmenu.query.all()
    print (g)
    return "ok"

The problem backs to from bookshelf import db, and if I delete that, the error will be changed to:

ImportError: cannot import name 'db'

bookshelf / mydatabase.py

from bookshelf import db

class pmenu(db.Model):
    __tablename__ = 'p_menu'
    id = db.Column(db.Integer, primary_key=True)
    txt = db.Column(db.String(80), unique=True)
    link = db.Column(db.String(1024))
    def __init__(self, txt, link):
        self.txt = txt
        self.link = link
    def __repr__(self):
        return "{'txt': " + self.txt + ", 'link':" + self.link + "}"

Any solution?

Wot answered 24/1, 2017 at 12:51 Comment(0)
I
59

This is actually a simple, yet frustrating issue. The problem is you are importing main BEFORE you are creating the instance of db in your __init__.py

If move the import to after your db = SQLAlchemy(app), it will work:

from flask import Flask

from flask_sqlalchemy import SQLAlchemy

app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql+pymysql://uername:password@localhost/test'

db = SQLAlchemy(app)

from bookshelf.main.controllers import main #<--move this here

app.register_blueprint(main, url_prefix='/')
Interphone answered 24/1, 2017 at 22:11 Comment(11)
Yes correct :D the problem is fixed and I've learnt it, thank you :)Wot
how do i fix that if i try to create the db using command promptAmmonium
@omah94 I would suggest posting a question with your details, and code snippet to get the proper help. It will be difficult to determine your issue without that.Interphone
am having the same issuePhallic
Is there a way to add a linting rule for this? My editor sneakily puts back the import to the top of the file; I can't think of an alternative (other than disabling linting for app/__init__.py)Casein
@PratikK. what editor are you using? I've never, ever had this issue. I use PyCharmInterphone
It's moreso a pylint issue than an editor issue I guess, but I use vscodeCasein
OMG thanks, have been banging my head against that one for hours.Manse
@Manse Glad it could help. I remember when I banged my head for hours on this!Interphone
thanks a lot, especially for "but frustrating" bit - really sweetened the pill (not being ironic)Huh
Struggled with this for hours myself :(Carlstrom

© 2022 - 2024 — McMap. All rights reserved.