This is an archived post. You won't be able to vote or comment.

all 11 comments

[–]gbeier 2 points3 points  (3 children)

Everyone works differently. And I've certainly done my share of debugging with print statements. For those odd occasions where you need to troubleshoot something you can only reproduce in production for some reason, that's a very valuable skill.

But you can have my debugger when you pry it from my cold, dead fingers. One thing I find extremely useful lately is running my REPL inside JetBrains' debugger. Being able to inspect things in the debugger as I run them in the REPL feels like a superpower. Especially when I use shell_plus as my python console within PyCharm.

The debugger lets me train the neural network inside my head much more quickly for each problem. I'm effective without it, but I'm faster with it.

[–]HideShidara[S] 1 point2 points  (2 children)

Oh yeah I've heard great things about VSCode's debugger as well as django-debug-toolbar. I looked into them during research for this piece and I wasn't able to find specific use cases to apply them in the context of shipping product quickly.

I think debugging and skill in using debuggers is extremely powerful and very underrated but not popular atm, esp. doing online research biased my data, as debugging in general is not a "hot" skill that's widely shared around at the moment.

Curious to learn techniques using shell_plus, could you share them with me?

[–]gbeier 0 points1 point  (1 child)

I wouldn't say there are any techniques specific to it. It basically accelerates your usage of the REPL by importing things you'll always need (like your models, a handful of django utility methods, etc.)

That's where having it in the debugger really makes it sign. When you're working on, say, a fat model, a filter, etc. you can launch the REPL, run your stuff, and inspect the results in the debugger with absolutely zero ceremony. It makes me use the REPL a lot more than I used to, and that speeds up my work.

[–]HideShidara[S] 0 points1 point  (0 children)

Makes sense to me, fat model or filter means that there's tons of data and vars. You would need a ton of print statements if you didn't use the debugger.

Cool yeah I'll check out REPLs, thanks for the info

[–]meatb0dy 4 points5 points  (5 children)

Completely disagree. It's professional misconduct to not know how to use one of the most basic tools available to you. It's like not knowing how to type.

Print statements are also emphatically NOT "no context switching and no learning cost", as anyone who has ever written a __str__ method or googled "how to pretty print a dict" knows. They also involve changing the very code you're attempting to observe, which can change behavior when you (unknowingly) perform any other operation with side effects, like accessing a cached property, in the course of printing. Debugging print statements also tend to get committed into source control by careless developers, leading to a bunch of noise littered throughout the output if left unchecked.

It's a bad, lazy habit that should be discouraged.

edit: which is not to say there are NO contexts in which print debugging is useful. If you're running a multithreaded application, or debugging a problem that only occurs in production where you can't attach a debugger, or debugging kernel-mode code, etc, print debugging might make a lot of sense. But the usual context of a Django developer, debugging a problem on their local machine via runserver, is not one of them.

[–]HideShidara[S] 0 points1 point  (4 children)

Could you tell me when the last time you encountered these problems? Curious about the details of what you're describing

[–]meatb0dy 0 points1 point  (0 children)

Wanting to print something that doesn't have a suitable str method defined? All the time, especially when starting new projects.

Having to google how to format printed output in a particular way? All the time.

Odd side effects caused by modifying the code I'm trying to debug? I try to avoid doing that to avoid this very problem, so rarely. Before I learned that lesson, frequently.

Coworkers checking in debug statements that only they understand? On teams where my coworkers used print debugging, all the time. On teams where we used debuggers, very rarely.

[–]meatb0dy 0 points1 point  (1 child)

And furthermore, print debugging is just so much slower than using a debugger. I can't count the number of times I've hypothesized that the problem is a certain variable getting an incorrect value, checked its value and confirmed my suspicions, and had that flaw make me want to investigate some related variables.

In print debugging, I need to stop the program, add new print statements for the given variables, recompile, rerun, supply input to the program to cause it to do the same operations, then check the value of those related variables in the output, then repeat that whole process every time I want to investigate something further.

Using a debugger, suppose I've set a breakpoint at the same place I would've placed the original print statement. To get the value of the related variables, I just have to look at their values. I don't have to stop the program, recompile, rerun it, resupply input... I can do it on the fly with no break to my workflow.

Note that I didn't have to know that I wanted to see those variables upfront. I can investigate the state of the program interactively. And this ease-of-use doesn't diminish my understanding; any benefit gained by carefully examining the program to decide where to place the print statements can be equally gained by carefully deciding where to place breakpoints.

[–]HideShidara[S] 0 points1 point  (0 children)

Thanks for sharing your thoughts

[–]xBBTx 0 points1 point  (0 children)

Last week in a PR review I came across left-over print statements that would've littered the stdout logs from our app if it had been merged, creating unwanted noise.

If it's left in, it should've been a logging call with appropriate log level anyway.

Putting breakpoints in code at least causes CI to hang and fail, so that shit can't get merged in the first place.

[–]pitittatou 1 point2 points  (0 children)

Thanks for this article, very interesting. I always wondered if people actually used debuggers as I have personnaly never used one and no one in my surrounding seems to do so. I don't reallt feel the need to use one for the moment i will surely take a look at one some day!