Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

I want to introduce the concept of unit tests (and testing in general) to my co-workers; right now there are no tests at all and things are tested by actually performing the tasks via the UI to see the desired result. As you might imagine, the code is very tightly coupled to the exact implementation - even resulting in code that should be in a class and reused across the system being copied and pasted across methods.

Due to changed requirements, I have been asked to modify a module I previously wrote and that is fairly loosely coupled (not as much as I would like, but as best I can get without having to introduce a lot of other concepts). I've decided to include a suite of unit tests with my revised code to "prove" that it works as expected and demonstrate how testing works; I'm not following true TDD as some of the code is already written but I'm hoping to follow some TDD concepts for the new code I'll have to create.

Now, inevitably I'm sure I'll be asked why it's taking me more than a day or two to write the code, since parts of what I'll be interacting with already exist in the system (albeit without any tests and very tightly coupled), and when I check the code in I'll be asked just what this "Tests" project is. I can explain the basics of testing, but I can't explain the actual benefits in a way the others would understand (because they think testing requires you to run the app yourself, since often the actual UI matters in determining if the feature "works" or not). They don't understand the idea of loose coupling (clearly evident by the fact nothing is loosely coupled; there aren't even any interfaces outside of the code I've written), so trying to use that as a benefit would probably earn me a "Huh?" kind of look, and again I can't be as loose as I would like to without having to rework several existing modules and probably introduce some kind of IoC container, which would be viewed as wasting time and not "programming".

Does anyone have any suggestions on how I can point to this code and say "We should start creating unit tests" without coming off as either condescending (e.g. "Writing tests forces you to write good code." which would probably be taken to mean code except mine is bad) or without making it seem like a waste of time that doesn't add any real value?

share|improve this question
1  
This sounds like the time I asked the "Expert database guy" why the credit card info was A. unhashed and B. Why the phone number field was nvarchar(MAX) and C. Why there was no relationships between any of the tables. He just didn't get it. –  The Muffin Man May 23 '11 at 12:42
    
(this is a sarcastic answer, its a joke) -> (A) If some breaks into your database server you have bigger issues. (B) Data storage is cheap, and what if one wanted to store meta-data within a field. (C) NoSQL baby ;) (Again let me iterate I'm joking) –  Darknight May 23 '11 at 12:56
    
There's a whole chapter on this in the great The Art of Unit Testing. –  StuperUser May 23 '11 at 13:03
5  
@Wayne, Everytime I read one of your questions I am convinced that you need to find a new job. They are a stodgy outdated relic in software development and you aren't. If a window opens up for you jump for it and don't look back. –  maple_shaft May 23 '11 at 14:32
2  
@WayneM, Quit. Seriously. –  AK_ Feb 2 '12 at 16:50

6 Answers 6

up vote 11 down vote accepted

I want to introduce the concept of unit tests (and testing in general) to my co-workers

I think it might be better to start from the practical, not the conceptual, side. Of course, if you find during casual discussion that your coworkers and/or management are interested to hear about unit testing, all the better - then you may google up some concrete experiences / evidence from the web, put together a brief training, etc. However, from what you describe, it sounds like your teammates aren't very open to this strange new idea.

In such a situation, I would just start writing my little unit tests without trying to explain too much to anyone first. Add a couple of them whenever I change code, without trying to thoroughly cover all the code (which would take an inordinate amount of time). Ideally, if I manage to strike a fine balance, by the time they notice I am writing unit tests, I may already have a substantial test suite, and some concrete results to show (like "with this test case I managed to catch a bug introduced by last week's change, which would have otherwise slipped through to QA/production"). That will prove the tests' worth to any serious developer.

After that, I am in a good position to start explaining the long term benefits of unit testing, like

  • it proves that the code works - anytime, anywhere, instantly and automatically, which in turn
  • gives confidence to refactor, resulting in improved design and better maintainability,
  • and if something gets broken, unit tests give you (almost) instant feedback, as opposed to several days' or weeks' latency if the bug is caught by a separate QA department. Which usually enables you to fix the bug in seconds, instead of debugging for hours/days, in code which has long since dropped from your short term memory.

See also this related thread: Automated unit testing, integration testing or acceptance testing.

And an earlier one from SO: What is unit testing?

share|improve this answer
3  
+1 for the practical aspect. We did this in our 50+ dev. shop and it's catching on. Every time we get one more dev. writing the tests, they are hooked. –  ale May 23 '11 at 13:07

Do the math

  • tmt = the time required to manually test everything you conceievably might affect
  • twt = the time required to write the tests
  • k = the number of times you'll probably have to test everything before releasing the new code

    if (twt < tmt) or (twt < (k* tmt)) then it's a no-brainer: writing the tests will speed development.

otherwise look at the ratio (twt / (k* tmt)). If it is a very large number then wait for another opportunity; otherwise justify with regression-testing benefits.

Note: I suggest at this point to only test features, not units - much easier to justify and understand, and arguably less work with higher value than mere unit tests when refactoring.

Note 2: the time is takes to run the tests does not matter, because they're automated. You can do something else productive while the tests run, unless the tests take so long to run that they'll make you miss the deadline. Which is rare.

share|improve this answer
    
I'm giving you a +1, but that math looks scary! –  Wayne M May 23 '11 at 20:38
    
@Wayne it's just the subscripts, they are intimidating. But programming is not for sissies! ;-) –  Steven A. Lowe May 23 '11 at 20:40

As I always recommend, if you know of a great practice, the best way to introduce it gently into your environment would be of course to start doing it yourself and then somewhere along the way, some of your co-workers will see the benefits and pick it up.

The keyword here is evolution, not revolution.

share|improve this answer

While working on source code which doesn't have automated tests, We have to work with lot of care and needs more reviews to stay confidently that kind of changes we are making doesn't break any of the existing functionality.

When we have good automated test cases, the consequences will be quicker, confident and fearless development (it can be bug fixing, enhancement or re-factoring).

share|improve this answer

One suggestion if you are a Microsoft shop: find some documentation on MSDN that recommends unit testing or loose couping as a best practice (I am sure there are multiple instances of this) and point at it if there are conflicts.

It may sound like a crass way of doing things, but I have found that using the term 'best practice' will take you a long way especially with management.

share|improve this answer

Re-factor without Fear

As a slightly different angle, TDD allows you to "re-factor without fear", and this is a key benefit you can sell your team. It stops developers from saying to themselves:

  • "I don't want to touch this code because I'm afraid I'll break it"
  • "I don't want to write new functionality on to pof this code because I don't know how it works"
  • "Secretly, I'm afraid of that code"

I could harp on more, but this is well covered ground such as Uncle Bob on TDD and Martin Fowler on TDD.

Dependencies

Oh, I'll add one more thing. It will show them how TDD forces good design which enables you to cleanly deal with dependencies.

Bob: "Oh c%^p! The bosses just forced us all to use MS SQL Server 2008" Jane: "That's OK, the damage in minimilised because we DI our datasource and our DAO classes, I'm so glad that TDD encouraged us down that path."

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.