This blog has been moved to http://info.timkellogg.me/blog/

Wednesday, April 20, 2011

Scripting with rake

Rake is a great twist on traditional make (honestly, I never really liked Ant or NAnt). On the surface it looks more like make than Ant or Nant, but you can leverage the full syntax and standard library of Ruby (and there's no weird rules about tabs). As a .NET developer, albacore augments rake nicely with tasks for MSBuild (building Visual Studio projects and solutions), NUnit, ASP.NET precompiler, modifying your AssemblyInfo.cs (like for bumping the version number), and many more.

Since rake is just ruby code, you can do just about anything, but most file manipulation routines are even easier to write in rake, because most everything is already imported and ready to use. Unlike make, Ant, and Nant, you don't have to start a separate project just to develop tools to use in a rakefile, just write a ruby function!

Building dependencies first
A lot of people who aren't already familiar with build languages make some common mistakes. Among them, not using dependencies correctly. For instance, given a website solution that references framework

msbuild :framework do |msb|
  msb.solution = 'framework/src/framework.sln'
end

msbuild :website do |msb|
  msb.solution = 'src/website.sln'
end

task :default => [:framework, :website]

The default task is the task that's executed when you just type rake at the CLI. The reason this is terrible is that it's procedural and inflexible. Now, if I do rake website the build fails because framework hasn't been built yet. Instead, each task should specify what other tasks it directly relies on. This script should change to:

msbuild :framework do |msb|
  msb.solution = 'framework/src/framework.sln'
end

msbuild :website => :framework do |msb|
  msb.solution = 'src/website.sln'
end

task :default => :website

This way both rake and rake website work the same. This leverages rakes dependency framework that is at the core of all build languages.

Using file tasks
The other point that people often forget is that build languages are oriented around files. Make tasks were oriented around questions like "does this file need to be created?". This is where rakes file task comes in very handy. For instance, the above tasks can become

$framework_dll = 'framework/src/framework/bin/Debug/framework.dll'

file $framework_dll => :framework

$website_dll = 'website/bin/Debug/website.dll'

file $website_dll => :website

msbuild :framework do |msb|
  msb.solution = 'framework/src/framework.sln'
end

msbuild :website => $framework_dll do |msb|
  msb.solution = 'src/website.sln'
end

task :default => $website_dll

This makes it so that framework and website are only built if they aren't built already and won't be attempted unless they're missing.

Arbitrary scripting
Rake is a great platform for hosting arbitrary scripts that you might write to automate your development process. I have scripts to bump the assembly version and subsequently commit to git, deploy to our test server, and I plan to make tasks to interact with redmine via it's REST API (something certainly not possible in NAnt). Basically, any little task that I might write a script for (which is quite a bit) can be imported into the rakefile and mounted as a task (yes, ruby is very modular).

Wednesday, April 13, 2011

Automocking containers are not just for mocks

In my last post I introduced MoqContrib's automocking container. In this post I want to describe what sets it apart from MoqContrib's previous automocking container and all other automocking containers that I've heard of thus far.

A Castle.Windsor contributor said that for unit tests, "it's recommended that you don't use the container at all, or if the test setup gets too dense because of dependencies, use an AutoMockingContainer." This is in response to a stack overflow question regarding how to remove components in order to replace them with mocks. There are others that agree with him.

I don't agree with Mauricio or Derek (from the links above). I strongly believe that there are several reasons to let an automocking container have real services registered that aren't mocks. The primary reason is for integration tests. This is where you are testing a system of modules, a subset of the entire system, but you still need to isolate those modules to just the system under test (SUT). So while the dependencies within the SUT are going to be implemented with real implementations, everything else is mocked. This is a partially mocked situation.

One of the big reasons to use an automocking container is just to simplify everything. Sure, you're setups are starting to get pretty long for unit tests, but sometimes you run into issues where there is already a component registered so you can't register a mock without first removing the original component. This is very tedious and totally ruins any love you might have had for your IoC container.

In MoqContrib 1.0 the container will favor the last component registered over everything else. This is handy because you can do setups by exception. For an integration test fixture you can setup everything as a production implementation and then just mock components as needed. You can also do it the other way and just override with production implementations. I believe this will lead to much cleaner tests and much less time tracking down "how that friggin' component got registered".

As far as the progress of a 1.0 release, I had originally said that it was going to be released last weekend. However, there have been some problems getting the community on board. I also realized that it was missing several important features. I will release a preview as soon as I get the current code stable.

Wednesday, April 6, 2011

Introducing MoqContrib Auto-mocking Container

The past couple weeks I have been working on an auto-mocking inversion of control container for Moq Contrib. The first results are almost ready to release in the form of an Alpha. The first container to be released will be Castle.Windsor, later we will release an Autofac container.

You will be interested in this project if you use an IoC container in conjunction with unit tests and mocking (with Moq). You probably find yourself writing setups like:

[SetUp]
public void Given()
{
 _service = Mock<IService>();
 Container.Register(For<IService>().Instance(service.Object));
}

[Test]
public void I_did_something() 
{
 var test = new TestThingy();
 test.DoSomething();
 
 _service.Verify(x => x.Something(), Times.Once();
}

When you use an auto-mocking container, the container will create mocks at resolve-time if it doesn't already have a component for it. So in the above example, the setup would drop out completely as there wouldn't be any need to explicitly create and register the mock:

[Test]
public void I_did_something() 
{
 var test = new TestThingy();
 test.DoSomething();
 
 _service.Verify(x => x.Something(), Times.Once();
}

We will release an alpha version of the Castle.Windsor auto-mocking container later this week. Soon after we will add an Autofac container and start working towards a regular release schedule. If you are interested, visit the site at codeplex and give feedback through the discussion groups.

Happy Mocking!