Welcome to Software Development on Codidact!
Will you help us build our independent community of developers helping developers? We're small and trying to grow. We welcome questions about all aspects of software development, from design to code to QA and more. Got questions? Got answers? Got code you'd like someone to review? Please join us.
Different behavior with relative imports when using flask vs py
I have a small new Python 3.8 Flask project with some relative import quirks.
For the DB I use SQLAlchemy with Flask-Migrate. My project has the following general structure:
controllers/
static/
templates/
app.py
controller.py
helpers.py
models.py
requirements.txt
The app.py looks like this:
from .controller import app
if __name__ == "__main__":
app.run(host='0.0.0.0', port=5000, debug=True)
And the controller.py like this:
from flask import Flask
from . import helpers
app = Flask(__name__)
app.config.update(dict(
SQLALCHEMY_DATABASE_URI = "...",
SQLALCHEMY_TRACK_MODIFICATIONS = "..."
))
db = SQLAlchemy(app)
migrate = Migrate(app, db)
from .controllers.static_controller import static
app.register_blueprint(static, url_prefix='/')
The import in the model is this:
from .controller import db
And for the controllers the import is like this:
from flask import Blueprint, render_template, url_for, abort
from ..models import *
Using this setup I can run the application with the command flask run
. However (likely due to a configuration error), I cannot use the restarter in that mode, because it shows an error that the python interpreter can't be found.
Hence I thought about using app.run
(as you can see in the app.py), which does work in my experience. However, when I start the app with py app.py
, I get this error:
Traceback (most recent call last):
File "app.py", line 2, in <module>
from .controller import app
ImportError: attempted relative import with no known parent package
I tried adding an __init__.py
to the working directory, but that didn't help either.
My question is: How can I use relative imports here without drastically changing the project structure?
1 answer
The following users marked this post as Works for me:
User | Comment | Date |
---|---|---|
luap42 | (no comment) | Oct 4, 2021 at 16:43 |
I don't have a py
command on my system; for purposes of this answer I assume it's an alias to the python executable.
Running a script from a file is not quite the same as importing it. A script given on the command line doesn't know it's a package (__package__
is not set). That's why relative imports don't work.
What you probably want is to run it by module path, not filename. Assuming your top-level project directory is named yourapp
:
python3 -m yourapp.app
Run this from somewhere that yourapp
is importable. Unless you've done something odd with PYTHONPATH, the parent of your top-level project directory should work. You can check importability from the current directory with python3 -c 'import yourapp'
or similar.
(even better would be to make a setup.py and use it to pip-install the package; then your working directory won't matter. But you specified no structural changes, so.)
0 comment threads