Several years ago I was down in Texas for my sister’s wedding. We were in town a few days early to help with the set up and all that jazz. One of my sister’s bridesmaids was anxious, to say the least. She was coming up with all sorts of problems that could happen during the wedding ceremony or reception. There was a seemingly endless stream of “What happens if the flowers are wrong?” or “What happens if the ring bearer trips?” or “What happens if the DJ plays the wrong song?” Until finally my mom, hearing more than enough of these questions, turned to her and said “What if, in the middle of the ceremony, ninjas fall from the ceiling and start attacking the wedding party?” (In case you’re wondering, I got my sarcasm from my mom.) That pretty much ended all the questions coming from the bridesmaid.
I had largely forgotten about that event. But recently I was thinking about the different project management strategies I’ve been a part of over the past 13 years. At one point in my career, we had a rather formalized process that went like this:
- Requirements signed off by the (internal) customer
- Developer writes a specification document based on the requirements
- Developer has a spec review with the senior developers on the team.
- Developer writes a design document based on the specs.
- Developer has a design review with the senior developers on the team.
- Developer writes code
- Developer has code review with senior developers on the team.
- Feature is included in the next release (happened every 6 months.)
With this path of development, design was emphasized heavily up front. If you didn’t get the feature right, or if key aspects were missed, the customers had to wait at least 6 months to get an up-to-date version. This meant that a lot of our design involved ninjas falling from the ceiling. Specifications would involve use cases that may not ever happen. We had to anticipate every single user interaction, every single operating system that it might be installed on (this was a Windows application.) So we’d have use cases in our specification document like “User changes resolution from 1024 x 768 to 800 x 600” because we didn’t know what resolutions our users had — only what was possible for them to have.
However, the longer I’ve been working as a developer, the more iterative the development process has come. The thought of not releasing an update for the next 6 months seems like a long time. While working on Salesgenie, we released every 3 weeks (with a few exceptions caused by natural disasters.) While working on QuickQuote, I would often release multiple times in a week, basically whenever a serious bug was fixed or a new feature released. For the internal projects I’ve been working on the past month, we’ve released multiple times A DAY thanks to our build server.
What iterative development has really helped with is that I don’t have to come up with “Ninjas Falling from the Ceiling” use cases any more. Why? Because even if we didn’t account for a use case, we’ll be releasing shortly and we can just include it in that next release.
This makes development a lot more fun for me. Now instead of sitting in loooong design meetings, spec’ing out every last detail, I can sit in shorter meetings and start working on the parts of the application that are essential. Instead of dealing with every possibility, I can deal with probabilities. For example, if I have the user create a username & password, what is the probability that they’ll use the same password they use everywhere else? Highly probable, I should probably look at using some sort of OAuth provider instead. How probable is it that someone will try to quote a 17 mile track of conductor bar? Not likely.
I shouldn’t write my software in a way that deliberately breaks if someone tries to quote 17 miles. But at the same time, I should be free to optimize the program in a way that quoting 17 miles of track isn’t efficient.
In the end, iterative development keeps the ninjas where they belong, hiding in the ceiling, instead of dropping down and attacking the party.