Monday, November 30, 2009

Putting it together series – Part 1: Testing Framework (NBehave, Rhino.Mocks)

Introduction

Whenever I need to put even a simple application together there’s always a whole bunch of infrastructure I need to put in place. For a WPF application this can include:

  • IoC Container
  • Testing Framework
  • MVP / MVVM Framework
  • Logging
  • ORM

This was recently the case when putting together the PDC downloader.  So I’m going to put a quick post around each of these areas. Besides the UI Framework everything else should convert over to ASP.NET without too much difficulty.

There is going no be no real example as I don’t want to complicate the solutions. Each solution will contain the minimum code to get the relevant area up and running, with the smallest example I can give. Once you have things going, Google will provide more advanced help.

Part 1: Testing Framework

The first think I end up needing in any solution is a testing framework, and currently my framework of choice is NBehave, a superb framework for writing any tests be it TDD or BDD.

http://nbehave.org/

In my case I’m using MSTest; I prefer Gallio/MBUnit but they current don’t work so well in VS2010. In any case, after creating a new C# project your referenced assemblies should look something like this:

image

So we are ready to put together our first spec! The example will contain a little bit of rhino mocks to show the integration NBehave has put around it.

So let’s write our first BDD Story.

protected override void Establish_context()
{
this.Story = new Story("writing our first nbehave spec");
this.Story
.AsA("person new to nbehave")
.IWant("a simple example")
.SoThat("I can better understand how to use it");
}

This story doesn’t actually do anything, however if we ran the NBehave tool we would have that output together with the scenarios. This way when a test fails, you know exactly which business functionality has been affected.

[TestMethod]
public void APlainOldNBehaveSpec()
{
SillyPOCO sillyPOCO = null;
string junglegon = "Junglegon";

Story.WithScenario("a plain old nbehave spec")
.Given("an object we are going to test",
()=> sillyPOCO = new SillyPOCO())
.When("we set a property on that object",
()=> sillyPOCO.Name = junglegon)
.Then("we should have changed that object",
()=> Assert.AreEqual(junglegon, sillyPOCO.Name));
}

There’s our first NBehave specification. It’s pretty straightforward, and I particularly like how easy it is to read when the Given, When and Then clauses are accompanied by a well written scenario. You might ask whether or not this why of testing scales when testing complicated business functionality or frameworks, and I can say it does. Even better than just working, it forces you to improve the quality of your test code to make it more readable and less bulky which is what my workmates and myself experienced on our current project.

Anyhow, let’s take a look at testing with rhino mocks, we are going to add some pointless dependacy properties to out silly object to test the interactions using mocks.

[TestMethod]
public void AnNBehaveSpecWithMocking()
{
SillyPOCO sillyPOCO = null;

Story.WithScenario("a plain old nbehave spec")
.Given("an object we are going to test",
() => sillyPOCO = new SillyPOCO())
.And("the object has a silly service",
()=> sillyPOCO.SillyService = CreateDependency<ISillyService>())
.When("we call a method on the object",
()=> sillyPOCO.TalkToService())
.Then("the service should have been called",
()=> sillyPOCO.SillyService.AssertWasCalled(service => service.Chatter()));
}

NBehave provides a CreateDependency method as a wrapper for creating a mocks. When making your expects and asserts, you can use the rhino mocks extension methods as a simple of way checking things happened the way you expected.

You can find the code for the examples at the bitbucket repo:

http://bitbucket.org/naeem.khedarun/projectpit/overview/

The samples for this part are under a tag called partone. Simply get the repository and update to that tag.

Friday, November 27, 2009

New balloon tip notifications for PDC Downloader

image

There are balloon tips for starting and finishing downloads. There is also one if the download errors for whatever reason, in which case mail me the log file!

download

New version of PDC Downloader

Incremental improvements this time based on requests.

  • Now logs all exceptions to a log file in Logs/<date-time>.log. If you have any problems just email this log to me and I’ll take a look and push out a new version with fixes.
  • Removes failed downloads from the download queue so you can try and re-download.

download

Wednesday, November 25, 2009

PDC Session Downloader Resuming is now fixed…

download

I hope so anyway…

PDC Session Downloader resume functionality

Seems to be broken… I’ll try and have it fixed by tomorrow.

Update to PDC Session Downloader

Based on some requests I’ve updated the application.

Changes:

  • Updated application to work with full sessions list so you can download all available sessions
  • Added ability to resume broken downloads.
  • Added ability to download sessions with strange characters in the description.

The repository has been updated with the changes, and a new download link.

download

Enjoy!

Doh! PDC Downloader

It looks like frank has updated his XML file (which my application uses) with some new sessions. Luckily the XML structure is abstracted away using a stylesheet tranform. I’ll update the application with the new file this evening.

PDC 2009 Session Downloader

So PDC 2009 is all wrapped up and for those of us not lucky enough to attend, we still have the sessions which are available on the PDC site http://microsoftpdc.com/.

This would have normally been enough for me, however Frank (http://www.franksworld.com/) was nice enough to provide a small utility to automatically download the sessions. The utility does work, but it did leave something to be desired (A non blocking UI, ability to choose sessions, etc…) so my OCD kicked in and I just had to do something.

I’ve built a little application which let’s you choose which sessions you want to download, and provide a way to see each downloads progress.

image

image

It wasn’t bad for a few hours work, however there’s some nice technology backing it and it’s a fun little solution to try new things inside.

You can find the full source code on bitbucket: http://bitbucket.org/naeem.khedarun/fancypcddownloader2009/overview/

It’s built using Visual Studio 2010 (Beta 2), and you’ll find inside some examples of using:

  • Parallel task library
  • WPF
  • NBehave (BDD) Specifications
  • Caliburn / Prism
  • Windsor IoC with Fluent Configuration
  • Xslt Transforms / DataContract serialising

There’s a few more things I plan to add, but so far I’ve got it downloading my sessions and that’s keeping me happy for now. If you do make any modifications feel to fork it on bitbucket and I’ll merge the changes in.

* Update new version*

download

Wednesday, November 11, 2009

Building a package management framework

One of the open source projects I’m currently working on is PiXI which you can learn more about here.

The project is essentially a framework which allows plug-ins to be added using MEF and MAF loaded out of a few plug-in directories. So writing a new plug-in for the framework is incredibly easy (I think…), however pushing plug-ins to users is still a real pain.

The current process would be:

  1. Create a WiX installer for your plug-in which deploys everything into the appropriate directories.
  2. Upload the plug-in somewhere.
  3. User downloads the plug-in from somewhere
  4. User installs it via the installer (which normally contains prompts and isn’t a background operation).

This is less than idea, in both distribution and developer effort, so moving to a new model is a good idea. And since MEF is really kicking off now a framework to more easily facilitate this process wouldn’t go amiss.

I would like this to follow a more unix like approach using the idea of packages. This is all available in Linux on more recently on smart phones however windows is greatly lagging behind in this respect. My current thinking for this process is split into three main areas:

image

The NPackageManager suite is a combination of tools, API’s and applications to allow for some flexibility in this process.

  • BUILD – This is aimed towards plug-in developers who need an easy means of packaging and deploying plug-ins. Currently NPackageManager contains a command line tool to package up a solution together with a package definition, similar to many Linux repo systems.
  • INSTALL – This is targeted towards the target application which needs to consume the plug-ins. Target applications need an easy way to setup the ability to consume generated packages and register associations in the registry. For all intents and purposed discovery of new plug-ins is left to the actual technology employed, for example MEF will take care of the integration aspect.
  • UNINSTALL – Again targeted towards the target application, a simple API to uninstall from a list of installed plug-ins should be provided (not there yet). This means an application can expose the functionality to the user without having to hand crank the un-installation code which should normally be similar between projects.

I’ve made a start on this (basically enough to move my own project forward) and will be blogging about improvements to this as time goes on.

http://bitbucket.org/naeem.khedarun/npackagemanager/

Using the configuration section designer

There’s an awesome tool which one of my work mates showed me called the Configuration Section Designer. It’s an open source project and be found on Codeplex here.

It really beats hand cranking a custom configuration and generates a nice API for using your new configuration section.

After installing it, it’s simple to add a new configuration.

image

This will split out a bunch of generated files, in my case:

image

The one we are interested in is the .csd file, which is where we go to edit the configuration section using the designer. So let’s open that one up, and we get a nice designer with some logical toolbox items:

image

I’ve created my custom configuration section with a single attribute called installationRoot:

image

When you try and save, the CSD attempts to validate your configuration section, and errors will appear in the usual visual studio error box:

image

It will want you to give the namespaces for where you want the generated files to go, in my case I used their physical location in the solution so everything matches. You can edit namespaces and xml namespaces as well as types for the attributes and everything else in the properties box.

image

It’s all quite logical and straightforward to use. It really comes in handy when you start putting together complex configuration sections and realise you have no code to write:

image

Consuming the generated API is also very straightforward:

[Test]
public void Create_WithValidConfiguration_HydratesStructureConfigurationObject()
{
Structure structure = NPkgConfiguration.Instance.structure;

Assert.AreEqual("package", structure.packageRoot, "Failed to hydrate correctly.");
Assert.AreEqual("installation", structure.installationRoot, "Failed to hydrate correctly.");
Assert.AreEqual("source", structure.sourceRoot, "Failed to hydrate correctly.");
Assert.AreEqual("document", structure.documentRoot, "Failed to hydrate correctly.");
}

Hope you enjoy using it!