flask run not finding module import but works with gunicorn

Having a module not found error ​when starting Flask like this:

$ python src/app/main.py

$ python src/app/main.py
Traceback (most recent call last):
  File "/home/james/code/webapp/src/app/main.py", line 3, in <module>
    from app.web import app_config
ModuleNotFoundError: No module named 'app'

Directory :

src
 |- app    
 |- |- __init__.py
 |- |- main.py
 |- |- web
 |- |- |- __init__.py
 |- |- |- app_config.py

main.py :

from flask import Flask

from app.web import app_config


app = Flask(__name__)


@app.get("/ping")
def ping():

    return "pong"

if __name__ == "__main__":

    app.run(debug=True)

But if I start it with gunicorn then it is fine:

$  gunicorn app.main:app
[2022-01-22 15:28:58 +0000] [148] [INFO] Starting gunicorn 20.1.0
[2022-01-22 15:28:58 +0000] [148] [INFO] Listening at: http://127.0.0.1:8000 (148)
[2022-01-22 15:28:58 +0000] [148] [INFO] Using worker: sync
[2022-01-22 15:28:58 +0000] [150] [INFO] Booting worker with pid: 150

Why is running Flask directly from terminal not letting it find higher level directory modules?


The app module is not found because of the Module Search Path of Python. It tries to import from main.py's directory.

If you don't want to change anything, cd into src/ directory, and from there use the "module method" to run the app:

$ python -m app.main

Second method: change from app.web import app_config line to from web import app_config, then the original python src/app/main.py will work because now it imports relative from main.py.

Third option: add the full path of src directory to PYTHONPATH env var.