Geeks With Blogs
Blog Moved to http://podwysocki.codebetter.com/ Blog Moved to http://podwysocki.codebetter.com/
Recently among other places it was asked on the altdotnet list about the strategies of unit testing with regards to assemblies and naming  This message here caught my eye regarding putting your NUnit tests in the same assembly as the code under test.

The message states about putting the tests in the same assembly :

There are a couple advantages to this approach:
  • The nearness of the files will make it easier (and therefore more likely) that developers will work on the test in tandem with the class under test (CUT).
  • One can make private methods on the CUT into internal methods and then write tests for them, if need be.
  • Will effectively halve the number of projects in the solution (My current solution has 40+ non test projects), making the solution explorer a little less unwieldy.
  • I'm thinking this will make it easier for devs unfamiliar with NUnit testing to gain experience with it faster. (I'm currently trying to introduce the concept to 10+ developers.)
And the only disadvantage I have thought of so far:
  • The production assemblies have a reference to NUnit and contain more types. Slower compilation and load time?
The DEBUG approach

I can say in the early days of my test driven development and others, I was doing this as were many others.  We'd go ahead and create a Tests folder inside our project which in turn would create a .Tests namespace.  In fact, most people were doing this with their test fixtures:

#if DEBUG

[TestFixture]
public class CustomerTestFixture
{
     ...
}

#endif

This would prevent of course it being compiled into your production build, had you of course used the release build type.  Many shops I worked with never did that...

Early on, I  realized that it clutters up your assemblies quite quickly.  Throw on top of that any unit testing dll of choice (MbUnit, NUnit, xUnit.NET, MSTest) and any mocking framework as well (Rhino Mocks, TypeMock.NET).  I was weary of including any references in my assemblies that I didn't absolutely need.

Testing Internals

One of the main reasons many advocate this approach is that they have access to the internals of your assembly to put them under test.  I think the early versions of the Enterprise Library were this way, although I can't remember.  I'm sure someone will correct me at some point.

By moving my unit tests to the outside in a separate .Tests assembly, I had to think long and hard about the public API I was willing to expose.  In a way, that's a good thing as it made me very clear on the boundaries of my classes and the assembly as a whole.  I also tend to have multiple tests fixtures per specification under tests as I want to test it under multiple aspects that may be cross-cutting.  I'm moving more towards a BDD way of doing things, albeit I'm in a mixed environment now of TDD with BDD.

Ultimately, though if you need to expose some sort of internals, although should not be the case with 99% of what you do, you have the option of internals visible to attribute such as this:

[assembly: InternalsVisibleTo("Podwysocki.Contracts")]

But to do any more than that, well, brings up a testing code smell and a rant.  I think a better approach is to use Dependency Injection and use that to set your expectations through mocks.  Then you can test the internals quite easily, but of course testing one expectation at a time and using a double for the other dependencies.  That's another lesson I've had to learn over time is the "When to use Mocks".  Then again I could be blowing smoke...

Rant Time

I've noticed in MSTest that you can create private accessors for your given objects under test.  This just to me screams of being a horrid idea.  Very likely during a lot of my refactoring, the internals of my classes under test can and will change frequently.  So, that means my unit tests will break quite quickly, then I'll have to right-click on my class again and generate my proxy methods again...

Oh, and generating your unit tests by right clicking on your class just doesn't seem very TDD to me.  I'm sure most will agree with me on this, and you wonder why there is xUnit.NET coming from Microsoft guys when MSTest already exists.

Conclusion

So, at the end of the day, I'm more for testing the publicly facing API of your given assembly.  That makes you think long and hard about what you want to expose and how granular you make your specifications under test.  It's been a long road since I've started TDD and even BDD and I'll admit I still have much to learn..

kick it on DotNetKicks.com Posted on Thursday, January 24, 2008 6:55 PM Visual Studio , Test Driven Development , Behavior Driven Development | Back to top


Comments on this post: Testing your internals inside out

No comments posted yet.
Your comment:
 (will show your gravatar)


Copyright © Matthew Podwysocki | Powered by: GeeksWithBlogs.net