I find there's a lot of confusion when it comes to what web developers or programmers are doing when they're working. There's also confusion when it comes to time estimates for jobs. When I estimate 40 hours for a web project a person may think, "Oh, so that should be done in week then?". However, I don't just sit there at my computer and type away until the application or website is fully built. No one would be happy if I did things that way, trust me.
Building a digital product is about the back and forth between the client and the developer. This is doubly so when working on a web application with custom functionality and an admin panel built from scratch. The sky is the limit when it comes to custom applications, and the layout/functionality can be whatever the end user wants (within reason).
I generally work on the project for a while at the computer, then I step away and do something else, and then return to what I was doing. This gives me some time to think about things a little more and give my brain and eyes a chance to relax. Also during the project life cycle, there are many times when the work needs to be reviewed by the client so they get a chance to adjust the course of things, add functionality if necessary, or make a design preference change.
Anyone following the DRY principle (don't repeat yourself), will want to assign lines of code that they find themselves repeating often to variables or create new functions. I prefer to write a little code, test it a bit, move a little further, and so forth. This prevents me from getting too far down the rabbit hole and then having trouble debugging the code when it runs.
Debugging and testing code is part of the project life-cycle. The tragedy occurs when so many clients, managers, and even developers don't take that into account. If Microsoft and Google has to debug their code, then your local developer will no doubt need to as well.
Luckily there are ways to cut down on the bugs and test while you build. One of the approaches I take is to test my code as I build it to ensure everything is working properly as I go. I have a bit of a spider sense when I start to write hackish or sloppy code. I begin to feel guilty as if a lead developer from Twitter is looking over my shoulder. At that point I realize it's time to step away and rethink things, or just call it a night.
This approach prevents me from going to deep down a rabbit hole that's just leading to a poor application.