The Art of Harvesting Abstraction
Filed Under Architecture
Often I watch senior developers so hell-bent on preventing DRY through code abstractions, that they fall victim to the YAGNI principle. By being proactive you are opening yourself to wasting time creating abstractions that may never be needed or worse adding unwanted noise to your code.
Refactoring to abstractions should be a reactive response to DRY, not a proactive prevention plan. Being reactive to problems is a very “agile” approach, but even practitioners of agile processes sometimes get caught with their pants down running BUFD centric practices. To combat this problem, I created a term to help others overcome premature abstractions – Abstraction Harvesting.
Software is like a garden, you can’t 100% force or predict what is going to grow; however, you can react to current situations to better steer results in a favorable direction. The only rule of software abstraction harvesting is that you must have target software to abstract. What is the purpose of creating abstractions, if you don’t yet have the problem-solving concrete implementations? This is the equivalent of running the tractor over the field before the first sprout is even visible.
Before software can be reusable it first has to be usable. -Ralph Johnson
If we look closely at both DRY and YAGNI we find an almost sequential relationship. Without a DRY situation, we can not have YAGNI, but it is apparent that you can have a YAGNI situation without DRY. This is the equivelent of putting the cart before the horse. The concept of “Abstraction Harvesting” helps put the order back in place so you can prevent both DRY and YAGNI.
Have you been guilty of premature abstractions? If so, I want to hear the horror stories…
5 Responses to “The Art of Harvesting Abstraction”
Damn city kids.
If you don’t run the tractor “over the field before the first sprout”, how the hell are you going to have a sprout?
Nice Mark 🙂
But more to the point, I work at a company where one of the requirements for a pay grade jump is that “designs do not have unnecessary layers of abstraction.” The way that I’ve always thought about this relates directly to your topic today. The key is to figure out what constitutes a “necessary” level of abstraction. One could spend significant time on up-front analysis trying to find the hot spots that require the abstraction, or one could be more agile and start coding and refactoring allowing the abstractions to “grow” as needed. Yet every day I see new features designed with many levels of DI and strategy patterns in an attempt to be elegant (or something) and I know they will never be “fruitful.”
One of the things that often doesn’t get asked as much as it should during interviews is regarding experience. If you want someone that can truly balance the level of abstraction I feel that experience is key.
@Jeremy –
Ah, but that is partially my point, sometimes experience gives us ego. That ego is what leads us astray in believing we can “out-think” the problem domain and preemptively strike with abstractions.
Experience can also be a negative in some cases…
@Max
Agreed, experience can give us egos, and some developers never get passed that point. I think through the cycle of “life” for a good developer the possible negativity from experience tends to bite them in the ass a few times making making the “super developer” a bit more humble.
Sort of one of those things your old man told you when you where an all-knowing teenager putting you in back your place.