The other day over lunch we discussed the first few chapters of Practical Object Oriented Design in Ruby (POODR) by Sandi Metz. One of the things that came up in our discussion was the notion of YAGNI and its intersection with design.
YAGNI (You Aren't Gonna Need It) is all about avoiding building things you don't need today. We can't predict the future so why build in features or architecture that we don't know that we need. Isn't it better to keep things simple and only focus on what we do need today? Yes, of course it is! Simpler is always better! Who wouldn't agree with that?
Design — this may shock some — is complementary to YAGNI; it's about organizing the code we do need today well.
While too much design fails by pursuing architectural perfection; not enough design fails because we've incrementally built ourselves an unchangeable, immovable system. These systems display the characteristic of a vicious cycle of stop and go development. A common sign is an increasing frequency of developer grumblings; something about a big re-write.
Wasting time on unnecessary things, YAGNI, is no better than avoiding spending time on necessary things. Besides, there are times and things you are just gonna need.
Finding a balance is where design comes in. It doesn't require years of experience, a degree, or some god-bestowed super power. The minimal requirement for good design is that you engage your brain; think about the goals you're building towards; identify the responsibilities to meet those goals; and put together a design that organizes which could guide the implementation.
Take careful warning however: the moment you start designing the system beyond the scope of the immediate goals, you have entered into the realm of YAGNI. There's no need to design everything, to figure out every possible detail, to determine how every eventual feature fits into the grand architecture. No, none of that. Design incrementally; keeping in mind immediate work coming up, but nothing beyond.
The design of the system should emerge over time as successive changes take place. This isn't to say that it emerges on its own; it doesn't. It emerges because at each step we are intentional with the design of the changes taking place.
This is easier than it sounds and it mostly involves stepping away from the keyboard; which, if you're not stepping away from your keyboard for at least 5 minutes before you begin work on a change to organize your thoughts, well, you're going to end designing by happenstance; don't.
Step away from the keyboard for 5 to 15 minutes; find a sheet of paper or a white-board, draw circles and lines and any thing that helps you organize your thoughts; then verbally communicate it to someone else.
I'm always amazed how far a little bit of intention and thought towards design can improve state of a system; maybe you will too.