Debug Python in VSCode
Debugging is one of those features that makes an IDE more powerful than a simple editor. It’s not hard to do and can save you many hours of frantically adding print statements to your code. So let us spend a little effort on learning the basics right now!Debug current file
Instead of using the ‘Run Without Debugging’ option, we’ll now go for the ‘Run -> Start Debugging‘ option. Alternatively, you can simply press F5. VSCode will ask you what you want to do. Since we want to run the current file, pick ‘Python File’.
The program will again crash with an error. But instead of stopping, the debugger comes in and highlights the line in which the error occurred. Since it’s complaining about the list index being out of range, let’s inspect the sys.argv list more closely!
When hovering over the text sys.argv, you get a popover that allows you to inspect the variable in detail. When hovering over sys, you will see lots of internals from the sys module. When hovering over argv, you’ll see the contents of argv:
Even though we didn’t supply an argument, argv still contains one element: the complete path to the current script. Something we didn’t anticipate! The OS always gives us the program’s name as the first argument in argv. All we need to do now is change the comparison to: if len(sys.argv) == 2. Restart the program by pressing the restart button at the top right or by pressing Control + Shift + F5 or cmd + shift + F5. It should now output ‘Hi there, stranger’ and exit normally.
Create run configurations
You’ve learned a quick method to start debugging by running the current file. However, you can create one or more run configurations if you want more options. Such a configuration allows you to store specific parameters, so we can start the program exactly how we want it to.To create a run configuration, click Run -> Add Configuration. Pick the ‘Python file’ option again. VSCode will create a launch.json file in the .vscode folder. This file is prefilled with an example configuration. Modify the JSON to look like this:
This configuration supplies an argument to the script: the name ‘Erik’. Note that it also specifically starts vscode_playground.py instead of the current file. You can now launch the debugger using this configuration. But first, let’s open the Run/Debug view in the panel on the left by clicking on the large run button with the little bug on it or clicking Ctrl+Shift+D or Cmd+Shift+D:
At the top of this view, you should see your newly created configuration. Start it by clicking on the play button next to it. The output should now say ‘Hi there, Erik’.
Breakpoints
At some point, you want to use breakpoints: a line in your program at which you want to explicitly pause the execution, or take a break, so you get a chance to inspect the state of your program at that point. Adding a breakpoint is extremely easy. In the left margin is an area that is often called the gutter. This is the space on the left side of a file where the line numbers are displayed. A faint red dot should appear when you hover there with your mouse, and it will turn bright red once you click it:If you run the program now, it will pause on the breakpoint, allowing you to inspect the variables at that point in time. To continue, you can click the continue button or press F5. The debugger will continue execution until it encounters another breakpoint or the program finishes.
Alternatively, you can execute the program step by step from here on by using the step over (F10), step into (F11), and step out (F12) buttons. This way, you can execute the program line by line and optionally step into and out of Python function calls.
A few short notes on these step types:
- Step over: run the command on this line. If it is a function call, run the entire function instead of ‘stepping in’ and running the function line-by-line.
- Stepping in: follow (or step into) a function call and run that function line-by-line.
- Step out: run the function to the end, and return to the point right after it was called.
Run selection or current line
Another helpful feature is the ability to run a code selection or the current line you’re on. This won’t always be useful: often, a line of code or selection of code heavily depends on its context. But sometimes, it can come in handy. To run a code selection or the current line, press Shift+Enter or use the command palette and search for ‘run selection in terminal’.
The code runs in a Python REPL, and once finished, this REPL stays open so you can experiment, inspect variables, etc. For example, if you ‘run’ a function, you can now call that function from the REPL since it is defined there.
A cool feature is that all subsequent commands to run a selection or current line are executed in this same REPL, keeping the state intact. So if you change the function and ‘run’ it again, the function gets redefined in the REPL. It’s a nice hack to test the code you just wrote, but it’s not a replacement for proper unit testing.
Running code from the terminal
VSCode has an integrated terminal, which can be extremely useful. Some people never use it, and others use it all the time. I’m part of that last group: I run my code from the command line unless I’m debugging. I also do version control on the command line. I find it very useful to be familiar with all the command-line tools. It allows me to perform crucial tasks without an IDE, e.g., on someone else’s PC, a remote terminal, or just a quickly opened terminal window instead of opening a complete IDE.
Besides my personal preference, there are several use cases in which it’s easier to use the terminal instead of the GUI. For example: when you are testing with command-line options. You can add options in a run profile, but using the terminal is quicker if those options constantly change.
So let’s also explore how to run your code from the integrated terminal window.
Step 1: Open the built-in terminal
Use the Command Palette to run Terminal: Create New Terminal, or use the shortcut Ctrl+Shift+` (that’s a backtick). A terminal should open at the bottom of your screen. By pressing that key combination again, you can create more terminal windows. You can quickly show and hide the terminal panel by pressing Ctrl+` repeatedly.
Step 2: Run your code
Don’t forget to activate your virtual environment if you have one. Next, run your Python file as you would with any other file:VSCode and Python Virtualenv
When using a Python virtual environment, you need to let VSCode know. As mentioned earlier, the way to do this is to select the interpreter from your virtual environment instead of the system-wide one.
To test this, let’s create a virtual environment first:
python3 -m venv venv
As you can see from the screenshot, VSCode almost instantly noticed that we created this venv and offers to use it:
Click yes, and you’re done! Alternatively, you can manually select this venv in the command palette (Ctrl+Shift+P) by typing ‘select interpreter’ and clicking on ‘Python: select interpreter.’
Formatting Python in VSCode
You can format Python in VSCode if you hit:- Windows: Shift + alt + F
- Mac: Shift + Option + F
- Linux: Ctrl+Shift+I (that’s an uppercase i).
- Or open the command palette (ctrl + shift + p) and start typing ‘format document’.
From now on, if you press the format shortcut while editing a Python file, you’ll notice that your file gets formatted according to the default rules of the formatter. If you want to customize these rules, you will need to look up (e.g., on Google) how to do that for the specific formatter you picked. Usually, you can add or modify rules by creating a specific file in your project’s main directory.
Saving a workspace
Finally, you might want to save your workspace. It’s not necessary, though. You can simply open the folder again. Customizations like your launch configurations are kept in the (hidden) .vscode directory, and VSCode will find this if you open the folder. However, if you opened multiple folders in your workspace and don’t want to repeat those steps continually, you can save the workspace using the File -> Save Workspace As.. menu.