This follow-up of debugging mindset goes into real life debugging. By now you know the perfect debugging mindset: curious, humble and suspicious. Debugging consists of understanding the problem, reproducing it, finding the problem, finding the right place to fix it and to perform some after-care.
Understanding the problem
The first preparation you want to make is to know what the correct behaviour is. Not just in this case, but also for all the edge-cases that can occur in this part of the code. Because these still need to work after you make your fix! The application(s) you’re debugging might be too big to understand completely though, so don’t try to understand it all. Some valid questions you want to ask;
- Which application is responsible for this?
- Which layer of the architecture is responsible for solving the problem? Think client side or server side. Think model, view or controller.
- Isn’t this actually expected behaviour? If it is, then you’re done.
- Is the input to the whole process correct? Maybe the problem is somewhere earlier in the process; this input should not be allowed.
Reproducing the problem
The second preparation you want to make is to reproduce the problem in your development environment. If you can’t, then try harder. This is really an essential part of solving the problem, because reproducing the correct conditions means you have a better understanding of what is going on. Maybe the problem exists because the configuration or the database schema isn’t synchronized between environments.
The best way to reproduce the problem is to make a unit-test that detects the problem, once you’ve done this you’re practically done.
Finding the problem
These are various tricks to find which part of the source code causes the problem. These are some tricks you can try in real life debugging
- Check your version control system. Recent changes could be related. Files that are often changed and have different authors are suspicious.
- Go at it from two ways. Sometimes you have the name of a file and a line number, but it can be hard to reason upwards from there. Try both top-down and bottom-up approaches.
- Use binary-search to reduce the amount of code you’re looking at by 50% per try.
- Talk to the duck.
- There could be something going wrong with multi threading.
- Use a debugger tool that allows you to step through the application.
- If all of that doesn’t work: find out how to gather more information.
Finding the right place to fix it
If you’ve found the problem by now, there is one more simple question to ask yourself: where in the application is the correct way to fix it? Sometimes the problem might be a problem that only exists once in the application, then it’s a candidate for a local fix. In other cases you might opt for a generic fix in a higher layer of the architecture.
Secondly, sometimes other code might depend on the wrong behaviour. So because you fixed the problem, something might break ahead in the process. This is, after all, a situation that hasn’t occurred in the rest of the code.
Real life debugging: The after care
In some cases there is some after care involved after fixing a bug. It’s something you might forget. After care is a pretty wide thing, I’ve seen cases where
- a field in the database was inserted wrongly, and it had to be corrected for previous cases.
- customers had received an incorrect e-mail, and there had to be sent an apology e-mail stating the previous message was incorrect.
- a check had to be made to prevent this error from occurring in the future.
Once all the after care is finished, you’re done!