views:

916

answers:

12

I'm collaborating with a group of professionals to put on an event to help teach the practice of TDD to people who are interested, but have no experience (novices).

We're trying to come up with labs, workshops, etc and I'm trying to think of the single, biggest thing that we need to impart upon these individuals to help them be successful in practicing TDD going forward.

What would you say we should make our priority for learning? Which aspect of teaching TDD is the most important. If you have to do two things, that's OK, I won't hold you to the SINGLE part :)

+8  A: 

Don't skip steps in the process. It takes longer to get into the initial groove of TDD, but once it's in place the entire SDLC is faster and far more bug-free.

Red - Green - Refactor -> just do it.

Chris Ballance
+1  A: 

In my experience, using TDD allows me and my team to mercilessly refactor our code without worrying that it will break something somewhere unexpected.

So I guess for me the most important aspect of TDD is coverage, since good coverage gives me the confidence to refactor whenever I see a spot in the codebase that can use it.

Andy
"In my experience, using TDD allows me and my team to mercilessly refactor our code without worrying that it will break something somewhere unexpected" - IMO, that is unit testing, not TDD. TDD forces you to think like a consumer of your code/design, and highlight weaknesses and problem areas.
Mitch Wheat
+7  A: 

Just because your tests pass it doesn't mean that the code is correct.

Aside from that, I'd say that it's important to consider testing in your design. If your code is difficult to test without intimate knowledge of the internal implementation of the unit under test, you may want to reconsider the design. Otherwise, refactoring becomes more risk prone because the tests likely have to be changed with the code.

+3  A: 

I suggest, "Be patient." It feels weird in the beginning. For me, it was probably three projects before it started to feel natural.

James A Wilson
+2  A: 

Dealing with the pressue of ditching TDD when deadlines are getting tight. This is one of the biggest issues I've came aross helping people and teams with TDD. They have had a trouble expressing the importance and value of dropping featured instead of tests to higher management.

Chris Canal
+28  A: 

It's about design. It's NOT about the tests.

Jon Limjap
Truer words have never been written on the subject!
Assaf Stone
+2  A: 

Proceed in baby-steps.

Make sure your tests only cover a very small scope and, as PhlipCPP says: 'Perform the MINIMAL EDIT needed to make the test pass.'

Even so, there is a lot to TDD, so you still have to make sure you don't miss anything out.

quamrana
A: 

Emphasize different kinds of tests. Both black-box testing and white-box testing are important and have different purposes. White-box testing is not there to verify correctness because it can't test the overall system. It is there to make code smells even stinkier and therefore provide a better refactoring direction. Black-box testing is there to test correctness. Every feature should be black-box tested.

Also, emphasize differences in test coverage. Due to combinatorial and repeatability problems, it is impossible to black-box test every code path in your application. My rule is that a feature isn't complete until it is black-box tested. You should help the students figure out their own rules. However, white-box tests should not have external class dependencies; therefore every line of every class should be white-box tested.

Heath Borders
+3  A: 

I agree with what Jon said in his answer, but I think an important corollary is that testability doesn't dictate "good design", but is only an indicator that your design in on target.

stevenharman
I can't really speak for Jon, but I think he means that it's not really anything about running the unit tests or the ability to get clear, orthogonal results (testability). It's about the design flaws you find when _writing_ the unit tests.
talkaboutquality
+3  A: 

I don't know whether this would count as the single most important thing - but it was something that took me some time to "get" when I was first exploring using TDD.

Don't write the code in your head before you write the test.

When I first started doing TDD I "knew" what the design should be. I "knew" what code I wanted to write. So I wrote a test that would let me write that bit of code.

When I was doing this I wasn't really doing TDD - since I was writing the code first (even if the code was only in my head :-)

It took me some time (and some poking by clever folk) to realise that you need to focus on the test. Write the test for the behaviour you want - then write the minimal code needed to make it pass - then let the design emerge through refactoring. Repeat until done.

adrianh
+1  A: 

TDD, in my mind, is all about the rhythm (red, green, refactor). Getting the rhythm down gets you over the "hump" of "not getting it". And if you don't get the rhythm down you likely won't stick with TDD for very long. The essence of the rhythm is baby steps, which has already been mentioned. Write as little code as possible, and refactor mercilessly.

One thing to emphasize is that TDD trades some short-term gains for long-term ones. Starting out with TDD will invariably lower your productivity. But once you learn the rhythm, it's akin to getting into a groove, and it can actually help you work faster. Not to mention the side-effect of TDD is an ever-growing base of unit tests that provide regression testing. One inevitability of software is that systems being maintained (without a suite of automated regression tests) degrade over time.

sliderhouserules
+1  A: 

Emphasize that TDD is a paradigm shift for developers. If you are standing up a new team, realize that it will take up to six months to get the team fully effective as TDD practitioners. Once you have a mature agile team effectively practicing TDD, pairing will enable a new developer to get into the swing a things after a couple of iteration. Furthermore, by using pairs from one team to seed a new line, you can get the new line up to speed on TDD much faster than the first line.

In the projects we have measured, we have seen a six fold drop in defects found during automated functional/ regression test once the team learned to do TDD. That is a significant savings. Furthermore, the code reflects a cleaner design, with fewer lines of code for each feature. TDD but a virtual stop to gold plating. TDD is most effective if you story cards have acceptance criteria.

TDD also enables sustainable pace. The team will find that they can continue to get the same number of features done with each iteration because the code remains clean with few defects. With both TDD and automated functional/ regression test, we often see zero defects found during User Acceptance Testing.

Cam Wolff