I'd like to share this page with people who, for whatever reasons, have been unable to adopt all of XP's practices in one go, but who are migrating towards it in whatever increments they've found possible.
I went for UnitTests first. In our engineering group (15 of us), nobody did any sort of unit testing. Code here has always been tested at the integration phase using test clients/servers and a debugger. Over the last six months I introduced UnitTests using a C++ version of JavaUnit (which I worked on and enhanced) and three of us are now using it successfully.
My evangelising of UnitTests to other engineers has received a generally lukewarm reception. Their basic objection has been the time involved in writing these tests. I know the arguments, but arguments are just words. They will need to see how my team's better tested software succeeds in the long term before they become convinced.
The two people on my team who I effectively forced to take on UnitTests are, they assure me :-), converted. I note they still prefer to do the older TestingByPokingAround first and I think that if they had to drop one of the two ways of testing they would go back to what they'd used before.
My boss likes the UnitTests because they give him a measurable level of confidence in the software (we achieve about 92-93 % code coverage) which he just can't get with ad-hoc testing.
So all in all with UnitTests, a good start, but still some way to go.
ReFactoring became possible once we had sufficient UnitTests to ensure good code coverage. I wouldn't say we have RelentlessTesting at present, and it's still possible for ReFactoring to break code because not all of our code tests are captured by our UnitTests, however we have enough confidence that we ReFactor with only a little bit of worry.
PairProgramming ran me up against the problem that engineers need to know that they can do the task by themselves (IndividualAchievement?). I backed away from this to a strategy of frequent code reviews, even rewriting code that I wasn't happy with. This sort of made me a co-writer of some of our software which led to CollectiveCodeOwnership, an XP practice which I am generally winning with vs the objection "I work better when it's my baby" (IndividualCodeOwnership?).
We did a BigDesignUpFront, but it wasn't that big. In summary I would say we followed the design, code, test cycle over a 3-4 month period, and that became our first iteration. Then we continued iteratively with UnitTests and ReFactorings. We did do some DesignDocumentation, enough to give us a road map (highest level abstraction) on our software.
I started with UnitTests also.
The way I have found works best for me is to just start doing it myself. As other developers ask questions, they find out what I am doing. As they look at my code, they see my tests. As we pair (to solve individual problems - we are not at the PairProgramming stage yet), they see how I work. Test first. Then code. We end up working less (read as writing less un-useful code). Nobody else has started using them but they all saw the point of the tests and agreed that they were useful. Maybe the question should be WhatStopsUnitTesting??
I also stress repeatedly that we should do the simplest thing. This leads to the idea of ReFactoring very nicely. The latter follows the former logically. It is difficult to explain ReFactoring unless you can actually show it in action. Some of the ReFactorings I do on a daily basis (MoveMethod, ExtractMethod) look very simple and people don't see it as ReFactoring. Developers look for a silver bullet and are disappointed when there is none. Maybe the best thing would be to do PairProgramming before worrying about teaching others to ReFactor. It's just too hard to explain without concrete examples. When people are paired then it should be easier for the driver to show his partner what ReFactoring is and how it works.
The other day I had a great reaction to CrcCards. We discussed the basic architecture a bit and I started writing class names on some index cards I had with me. By the time I started to add responsibilities the others were passing the cards around to see what was written on them. When we split up we just divvyed up the cards (and I didn't even have to mention that we should - one of the other guys just grabbed some of them and said "Okay, we'll do these ones and you do the others.")
-- IainLowe
I have had the same experience that when index cards are used, people adopt them very quickly. I think this is a great example of DoTheSimplestThingThatCouldPossiblyWork. Its a change from the top down. I think the resistance to Unit Testing is largely because it is a bottom up change, and the developers feel they are being made responsible for doing something they haven't volunteered or wanted to be involved in.
I think the other resistance to testing comes from the fact that most people don't know where to start. Which tests should I write? In programming, normally people pick an arbitrary start point, something they know how to do already, and just code from there. Maybe having people pick their start point, then writing the name of the test on the index card might help? Then they know their goal. I think this is the key:
Make the goal of development 'Having your tests pass' not writing lots of code. Form the project goals, rewards and milestones around that. This is where the cards and 5 minute meetings would come in helpful. Change the focus from writing lots of code to (workingless). - Todd Edman
See AdoptingXpPatternLanguage, AdoptUnitTestsFirst