Modular, Decoupled, Best Practiced, Well Designed, Bullshit
I write a metric crap ton of code. It’s pretty much what I do from the time I wake up until the time I go to bed on most days. I do it because I love it, but there’s something that’s always bothered me about code, or rather coders. All too often we try to make code perfect, when what we should really be trying to do is make it work.
We try to keep things loosely coupled, modular, and using the right design patterns. We apply all kinds of best practices, optimizations, and the latest paradigms. In reality though, if we make something that works, there will be time to go back and fix it, because making it work often means making money, which gives you options.
I’m not saying be sloppy. I’m not even saying to walk away from all these principles; they’re good. But don’t let them get it in your way of making something work. If you can take a short cut and have something working today, rather than “doing it right” and having it work a few weeks down the pike, then take that shortcut, note it, let your boss or client know about it, but do it, or at least give them the option. Sure, it might create more work down the road, but then again the client starts making money faster, and you get paid to come back and change it when they’re successful. It’s a win win.
[From my blog.]
If best pratices and good design principles get on your way of making something that work, they shouldn't probably be called best or good.
Best practices and good design principles should be there to give you more power to make things faster and better. Reducing features time to market, improving code reliability and predictability, making the business more reactive and more profitable.
Enforcing practices and design principles just for the sake of it is useless and counter-productive.
Any practices or design principles that gets on your way instead of helping you to achieve this should not be called 'best' or 'good' and be ditched in favor of really good ones.
If we can't find practices and design principle that helps us instead of getting on our way it's quite clear that ditching them is probably the less harmful thing to do. But really you should ask yourself "Can I find really good practises and principles".
> In reality though, if we make something that works, there will be time to go back and fix it, because making it work often means making money, which gives you options.
In my experience clients and bosses want to minimize expenditure, so coming back is never an option unless they want a new feature or other change. It works well if you're your own boss, or your boss/client actually works on the same code but that is the exception, not the rule.
Full disclosure: I mainly work the german market, but have also worked for people from Washington, Ireland, Finland where the above held true.
What Mithaldu says is mostly true, so I find this to be a tightrope (that being said, my current client is very, very happy to have me take time to go back and fix technical debt. This makes me happy).
I would just like to call attention to what I feel is the key qualifying statement of this post: "If you can take a short cut and have something working today, rather than “doing it right” and having it work a few weeks down the pike, then take that shortcut, note it, let your boss or client know about it, but do it, or at least give them the option."
If a shortcut will do the job for now, that is an acceptable choice only if you actually document why you took the shortcut. Even better if you actually leave behind some comments about what you would have preferred to do or plan to return and finish later.
In my experience (I'm usually the guy who comes in and owns legacy perl code when they want someone to support the app full-time) the technical debt left behind is rarely documented. If anyone was informed of the shortcut at the time it was authored, those individuals have long since forgotten or moved on to another job. So, for the sake of the Perl community and freelancers or full-time Perl hackers alike, please leave some level of "collateral" when racking up "technical debt."
@JT, yes, I'd have to agree with you (100%). I too write code from dusk til dawn most days and find myself, quite often, bothered by my own wanting for my code and/or architecture to be perfect. I think it's the curse of the craftsmanship.
I also believe that this is a key factor as to why many adept IT people (system architects, software developers, et al) have difficulty launching software products for themselves (i.e. too many choices and nobody telling them to "just do it this way for now").
I also feel that this has been validated in my own work experiences as many of the highly profitable companies I've worked for/with have products that are pretty crappy (from a UI/UX and/or coding POV), ... but even so, it works for the end-user and is thus a successful product.
I'd also venture to say that once you make the mental shift toward validated-learning based development (having customer feedback driving all code changes), it's then highly unlikely that you'll ever come back and refactor code strictly for the purposes of making it better.
This has to be balanced, and of course sometimes purism takes longer not because it takes longer, but because you haven't really grokked it yet (my last post on Dependency Injection and Providers shows this because it took me a while to get to a solution that wasn't a massive pain in the ass ). Though one could argue it's a lot more code than the simplest approach and in some cases that simple approach would work.
You have to strike a balance though, I've seen a 10k line if/then/else chain CGI, that had 0 abstraction. It's often faster to write 0 abstraction, and slower to write more abstraction, though more will get you places in the long run.
In some cases here in perl land I find that we lack the appropriate tools (for all them modules that exist) to do it right quickly.
@Al, interesting thought on why personal projects are hard to complete... I wonder what the solution to it is.