8
votes

i'm trying to debug an application (a web api) that use FastAPI (uvicorn) I'm also using poetry and set the projev virtual environment in vscode.

i read this tutorial to setup uvicorn and this one to setup vscode but i think i'm doing something wrong in set it up.

I tried to setup the launch.json both as python: module and python: current file

The problem seems that it doesn't recognize the project structure cause when i run the debug it stopped in an import statement with this error:

Exception has occurred: ImportError
attempted relative import with no known parent package

This is my current launch.json configuration:

"configurations": [
    {
        "name": "Python: local debug",
        "type": "python",
        "request": "launch",
        "program": "${workspaceFolder}/src/topic_service/service/__init__.py",
        "args" : ["--port", "8000"]
    },
]

I also tried to add a .env file setting PYTHONPATH:

PYTHONPATH=.:${PYTHONPATH}

Locally i run the application as follow:

poetry run uvicorn src.main:app --port 8080 --reload

Does anyone know how to correctly setup vscode to debug an uvicorn application?

Thank you

UPDATE: I also tried what this article says. the debugger seems to start but nothing happen (no breakpoint is triggered)

4

4 Answers

21
votes

Try this configuration.

{
    "name": "Python: Module",
    "type": "python",
    "request": "launch",
    "module": "uvicorn",
    "args": ["src.main:app","--reload"]
}
12
votes

Likewise you provide uvicorn module with necessary args during development of FastAPI application, you need to configure your launch.json located in .vscode directory with respective values.

I did a write up for custom project configurations to debug FastAPI in VS Code here

Suppose you issue the following command to run FastAPI on uvicorn server with args mentioned as below

uvicorn main:app --reload --port 8000

then your launch.json should have module with value of uvicorn and each of the args separated by space as items of the args array.

"module": "uvicorn",
"type": "python",
"request": "launch",
"args": [
    "main:app",
    "--reload",
    "--port",
    "8000"
],
"env": {
    "usersecret": "some$Ecret",
}

You can have this launch.json file in .vscode and then modify the args array in the JSON configuration as per your project structure.

{
    // Use IntelliSense to learn about possible attributes.
    // Hover to view descriptions of existing attributes.
    // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [
        {
            "name": "Python: FastAPI",
            "type": "python",
            "request": "launch",
            "module": "uvicorn",
            "env": {
                "db_username": "postgres",
                "db_password": "secret",
                "host_server": "localhost",
                "database_name": "fastapi",
                "ssl_mode": "prefer",
                "db_server_port": "5432"
            },
            "args": [
                "main:app",
                "--reload",
                "--port",
                "8000"
            ]
        }
    ]
}
3
votes

The quick and easy way: launch debugger F5 and then select FastAPI Debug Configuration: (p.s. this works on the VSCode Insiders; haven't tried it on a regular version)

enter image description here

1
votes

The way i debug is quite basic, hope it helps i have .py file with this config:

import uvicorn
from app.main import api

if __name__ == "__main__":
    dev = 1
    if dev==0:
        #use this one
        uvicorn.run(api, host="127.0.0.1", port=5000, log_level="info")
    if dev == 1:
        #or this one
        uvicorn.run('app.main:api', host="127.0.0.1", port=5000, log_level="info", reload=True, debug=True)
    if dev == 2:
        uvicorn.run('app.main:api', host="127.0.0.1", port=5000, log_level="info", workers=2)

and run the file with the vscode debugger, the important thing is to run the app with the debug flag because otherwise the debugger skips the breakpoints (at least in my case)