Stories about Software


The Larger Significance of the Royal TDD Rumble

Let’s Get Ready to Rumble

Tomorrow (this) morning at 11 AM Eastern time, the world is going to tune in on Pay Per View to the greatest rumble this side of the Thrilla in Manilla that pitted Muhummed Ali against Joe Frazier. Nearly 40 years after the original, the 2014 incarnation will pit the creator of Ruby on Rails against the creator of Extreme Programming and the TDD approach as well as an internationally acclaimed author and speaker in and about the field of software engineering. The venue will be google hangouts. Get your tickets before the internet sells out.

The reason for the brouhaha? A post entitled, “TDD is dead. Long live testing.” From there, a long series of subsequent posts, debates, arguments, etc ensued across the development world. So, after a couple of weeks of this, the battle was set between the TDD antagonist and a couple of proponents. Or something like this. (Might be that this isn’t a death match, since Martin Fowler explained, “We hope to be witty and entertaining, but we are more interested in exploring these topics in a way that expands our understanding of each others’ ideas,” but what’s the fun in that?)


Of late and I guess in general, I’ve written a lot of posts about unit testing, automated verification and test driven development, so suffice it to say that I’m a fan of this practice. So, one might think that I’d watch this hangout rooting for Fowler and Beck to win, the way I root for the Chicago Bears on fall Sundays. But to be honest, it doesn’t really bother me that someone, even a well-respected and widely known industry figure, doesn’t do things the way I do them. I don’t need or even want everyone to agree with me if for no other reason than this state of affairs would present me with new ideas to consider. If DHH doesn’t find TDD to be beneficial, I’m sort of curious as to why, and I might disagree, but it’s no skin off my nose.

Might Doesn’t Make Right

The tone of this post started off breezy and satirical, but I’d like to get a little more serious because I think there’s a lot of effort, money and happiness at stake. There are two competing attitudes at play in the hubbub surrounding this conversation and pretty much any tendency toward disagreement: “my way worked for me” and “my way is the right way.” I try hard — so very hard — to be someone who says or means the first thing. It is my sincere hope that this attitude permeates any blog posts I make, content I publish, and talks that I give — that they all have an implied “this is based on my experience, YMMV.” I might not always succeed, but that’s my goal. I take this with me at work as well; even with people that report to me when I’m reviewing code I don’t tell them what to do, but instead offer what I would do in their situations. I think this is critical with knowledge workers. It becomes a matter of persuading rather than forcing, which, in turn, becomes a matter of needing to earn respect rather than “might makes right.”

The reason, I think, that the Expert Beginner series resonated with so many people is because the Expert Beginner is “might makes right” incarnate, and it’s something that has invariably squashed your motivation and made you hate your life at some point during your career. Expert Beginners say “my way is the right way” and even “my way is the only way.” This is a characteristic of micromanagement and lack of vision that reduces knowledge workers to brainless cogs, and therein lies the effort, money, and happiness to which I referred.

I’ve left projects or even jobs to avoid “might makes right” Expert Beginnerism, and no doubt so have you. This is lost opportunity and value. Poof. Gone. 2 weeks notice, “knowledge transfer,” on-boarding, and starting all over. Running in place for organizations and projects.

Now, all Expert Beginners tend to think, “my way is the right way,” but not all people who think this way are Expert Beginners. In fact, some are legitimate experts whose way probably is a great way, and maybe even “the right way.” It’s human nature, I believe, to think this way. People form opinions and they want others to agree with those opinions. If we decide that a gluten free diet is really the way toward better health, not only do we expect others to be interested in our newfound wisdom and to agree with it, but we’re even offended when people don’t. I’ve been bored to tears watching this phenomenon take place over and over again in my Facebook feed.

As humans, we seem naturally to want our advice to be heeded, our opinions validated and our approaches mimicked. In my travels, I started doing TDD, and I found that it helped me tremendously and made me more productive — so much so that I post about it, create courses on it, and teach it to developers on my teams. So, if someone comments on a post about it saying, “that’s just a bunch of hippie crap,” my natural inclination is to be offended and to feel combative in response (and indeed, phrased that way, confrontation would appear to be the goal of such a comment, no doubt coming from someone who felt that my posts were an affront to the approaches he’d found to be helpful).

But I try to fight this as much as I can, and listen more to other people and see if I can understand why they do what they do. The irony is, this approach, counter to human nature, is actually in my best interests. I learn far more by listening to what others do than evangelizing for what I do. It’s hard to go this route, but likely beneficial.

Now, I’m not attempting a relativistic argument here to say that if someone’s experience is that they’ve “enjoyed success” by shipping non-compiling code that’s just as valid as someone who delivers reliable software. It’s not that everything is just a matter of feelings and opinions. Approaches and outcomes can and should be empirically measured and validated so that objective, collective progress can be made. Approach X may indeed by better than approach Y, measured by some metric, but those in camp X should be persuading and demonstrating, rather than shouting and flaming.

I doubt the software industry is unique, but it’s the one with which I’m familiar. And it’s frankly exhausting at times to see how much time people spend getting worked up and defensive because someone doesn’t share their love of some framework, approach, or technology. It becomes heated; it becomes personal. You’re an unprofessional hack because you use programming language X. You’re a sellout because you buy tools from company Y. My goodness people, settle down. Honest debates and exchanges accomplish a lot more for everyone. The esteemed gentlemen having the hangout tomorrow to discuss the merits of TDD seem to be favoring the “cooler heads” approach and it’d be nice for everyone to follow suit.

I think test driven development is the best approach to writing software to which I’ve been exposed (of course, or else I wouldn’t do it). I think that if you have an open mind and are willing to try it, I can persuade you that this is the case. But maybe I can’t. And maybe, there’s some as-yet undiscovered approach that someone will show me and I’ll be sold on that instead. Whatever the case may be, I’d like to see these types of exchanges favor attempts at persuasion as opposed to shouting, heated personal exchanges, or, worst of all, “might makes right” types of fiats. And, I think at the end of the day, we all need to come to grips with the knowledge that not everyone out there is going to share our opinions on the best way to accomplish a task. And hey, if your way is really better, it sure looks like you have a competitive advantage now, doesn’t it?

  • Great post, well-written. I, too have found it much better to approach things from the perspective of “This is what works for me” and/or “My understanding is . . .” These attitudes seem much more conducive to positive interchange of ideas than “This is THE way to do this” or mistaking my opinions for facts.

    Keep up the great work!

    • Thanks! And yeah, passing off opinion as fact has always been a pet peeve of mine — completely agreed on that count.

  • Geoff Mazeroff

    Your point about stopping, listening, and trying to understand is crucial. It seems like we spend so much energy trying to protect our ego that we may miss opportunities to have our minds expanded.

    Personally, I read the first few posts about “the war” and then tuned everyone out, realizing it had become a pissing match among heavy-hitters. Thank you for a rational response to the situation; I always enjoy hearing your point of view (even if it’s similar to my own!).

    • The tuning out was kind of what happened to me as well. I usually read pretty much all of Bob Martin’s posts on the 8th Light blog, but with the back and forth on this one I just found myself not interested, even though my feelings on TDD are very much in line with Bob’s.

  • Excellent post, I really like the part about “my way worked for me” and “my way is the right way.” – really great stuff

    • Thanks! I’ve found that people seem to respond well to conversations when I approach them with a mental framework of “I’m not sure what THE way is, but here’s what I did that seems to get the job done.”

  • Jordan Whiteley

    I’ll be in on this discussion because pure TDD has failed when I do it a number of times. When ever I start a project with TDD I start out well, then as the project neared completion and the clients started requesting changes I’d be bogged down with maintaining hundreds of tiny tests that broke because they were testing pedantic conditions that no longer made sense.

    My red green refactor mantra boiled down to: write one failing test, 2 line code change to make it pass. The new feature is contrary to an old feature so delete 4 failing tests that are no longer reflect the reality of the class. Fix a couple tests that were pedantic about a something but still reflect a requirement. Refactor the code, go through and fix another 6 tests that failed because I cleaned up a method signature.

    The above description may sound like I’m complaining about the time I spend rebuilding the tests. I’m not, most of the refactoring goes quickly. Instead think about the context switch between iterations. That’s what bugs me. I’m basically coding 1 minute in a project, then context switching and spending 2-5 minutes coding a living design document, then context switching back.

    Instead I’ve moved to a more systems testing stand point where I start out with one test per requirement of the customers request. I might even start by breaking the customers request into 4 or 5 testable requirements and pretending I had an ideal and easy to test class that solved all my problems (then abusing generate method stub liberally). I have found that this method generates far fewer tests that mean more to the client. Yes, it leaves some edge cases exposed, but I normally wind up with 4-5 tests and 40-80 lines of code rather than 40-50 tests and 300-500 lines of code.

    Bah that was a long comment.

    • I think that what you’re describing here is the essential, legitimate drawback of automated/unit testing in general, with TDD being no exception. I’ve come to be of the opinion that every single line of code in your application is a liability, which means that every unit test written makes your code base ‘worse’ (or at least more dangerous from a maintenance perspective).

      Now, before anyone thinks I’ve completely lost it and reversed my take, I believe that unit tests are net good. Their existence creates technical liability, but the good they do by documenting the code, verifying expected behavior and allowing fearless refactorings offsets the liability…. up to a point.

      And, I think “pedantic” is a great way to start describing where that point lies. (And I’m starting to think that I might make a post where I flesh out my thoughts in less ad-hoc fashion). It sounds like you’ve addressed it with more of a BDD/outside-in kind of approach, which I’ve also found myself doing at times.

      Another thing that’s helped get rid of some of the more obtuse tests that I write in early TDD phase is that I cannibalize them. I think I’ve done this a few times in my Chess series, but I’ll write a test saying that some new method I’m about to write doesn’t return null, for instance. Well, that’s ultimately a stupid test, even though it’s useful at the moment. As I move on, however, I don’t leave that test — I rename it and give it a more targeted condition that means more in the context of the application. I’ve found this to be helpful for limiting the number of “who cares” tests in the code base that you just delete when they go red.

  • Jerry

    Zealots tend to remain zealots, even when the things they’re zealous about change. Anyone who says, “at times I got sucked into that fundamentalist vortex” (nice syntax there, as if he’s an unwitting participant), will probably get sucked into fundamentalist vortices over and over. My guess is, this anti-TDD screed is the leading edge of the new fundamentalist vortex. For my part, I give it a resounding “meh”.

    • I don’t know much about DHH and the circles he travels in, having never dabbled in Rails at all. When I saw his post and Bob Martin’s response to it, I kind of skimmed both and cataloged what was going on as “yet another needlessly testy to TDD or not to TDD argument,” but your comment on DHH’s rhetoric made me go back through and give it a more careful read.

      To give him the benefit of the doubt, I wonder if his post was an exasperated response to people telling him about “the one true way,” but it is certainly designed to be provocative and heavy with veiled insult. I identify a couple of subtle logical fallacies in there people use a lot in conversation to great effect: middle ground and “I used to think like you but then I got wiser.”

      Middle ground being a situation where you paint the opposing perspective as characterized by frothing extremism, claim a bit of common ground with them, and then suggest that your position is inherently the right one by virtue of the fact that you’re in the middle. The “I used to think” fallacy is one I most commonly see in political arguments: “I was a liberal too when I was young, but then I got older and wiser.” It’s a back-handed, seemingly unassailable combination of ad hominem and circular reasoning. If you were to state it plainly without the dangling insinuation, the argument would be, “If we assume that I’m wiser and more enlightened than you and that I’m right about TDD, this whole situation is explained by you not having yet figured out what I’ve figured out, which is that TDD isn’t the right approach.”

      (I personally find the “I tried it for a while and then grew up, so I’m right” canard to be one of the most undercover-obnoxious tactics to use in an argument, but this probably makes me a hypocrite because it’s also one of the easiest to fall back on in the heat of an argument)

  • Terrific. My emotional reaction to DHH’s rhetoric-heavy argumentation was to want to calm down enough to enumerate the obvious holes in it. Gary Bernhardt did a masterly job of that. My next reaction was to want to mention that DHH had inflamed my passions and so I’m going to try to dispassionately revisit my attachment to TDD. But that posed two problems: (1) I couldn’t edit out enough ideas that didn’t need to be there, and (2) it was a lie. I had already been revisiting my attachment to TDD and DHH did precious little to illuminate or motivate further introspection. So the only topical reference in my post is to my own recent work experience, and barely even that. This post happens to represent my own feelings and is what I would have hoped to write if reaction #2 had panned out for me.

    • I now can’t get out of my head the mental image of some deranged project manager with a gun telling you, “God help me, if I see so much as a single assert…” 🙂

      Anyway, I listened to the hangout, but didn’t find the conversation to be particularly memorable (maybe the subsequent ones will be). What I’d be interested to understand is, cutting through all of the evocative imagery and subtle mudslinging, “what are DHH’s pain points, and what does he do that he thinks is a better alternative and might also be relevant to me (i.e. if it’s Rails-specific, this is all a non-starter for me at the moment)?”

      With me, the visceral attachment to TDD is pretty simple to explain (though less simple to justify empirically). I’m addicted to the tight feedback loop and the feeling of steadily winning lots of small battles, in the same way I would keep playing Civilization for many hours after I knew me taking over the entire world was simply a matter of time. Those things make software development really pleasant, but proving that they add value is a lot harder.

      This is getting to be kind of a long comment, but I’ll leave off saying that empirical validation of approaches is something I plan to start visiting a *LOT* in the future, and not only with posts, but perhaps with actual software and maybe even a venture. I think the ratio of anecdotal ‘evidence’ to measured experimentation in our industry is woeful and it’s time to do something about it.

  • Pingback: Information Exchange Realpolitik: Pushers and Pullers | DaedTech()

  • Thomas Lassanske

    While this post was written a couple years ago, the Facebook reference (and today’s share of this post) is more valid than ever, with the current political climate…