We’re doing some Silverlight development at work and I’m doing some off to the side. I like to stick with a familiar, proven unit test framework. NUnit 2.5.1. has some great new attributes to use during testing (actually these came out in 2.5) such as Timeout and MaxTime. To take advantage of them you have to have a version of NUnit compiled as a silverlight library or at least recompiled referencing the core of silverlight (system.dll and mscorlib versions 18.104.22.168).
In the spirit of continuing what a few other people have done, I have compiled the latest version of the NUnit framework into a SL library and want to make it available. The work of the following guys has helped me use NUnit up to version 2.4 and helped me get 2.5.1 going as well!
A nice template that included the SL framework version, if someone wants this updated please let me know and I can do that too, otherwise I’ll just post my dlls:
A set of instructions to port the framework to SL (I diverged on some of these, see below):
Here is the list of changes and what didn’t make the cut:
- BinarySerializableConstraint - SL core doesn’t have BinarySerializer
- AssertionException, IgnoreException, InconclusiveException, SuccessException - cannot be serialized, SL core doesn’t have SerializationAttribute (goes along with BinarySerializer)
- RequiresSTA and RequiresMTA attributes
How was this pulled off?
- For both the nunit.framework and nunit.framework.tests I added new silverlight libraries and copied the links to the code that the respective projects already referenced. I also added a nunit.silverlight to drop in some of the following additional classes that are needed but not in the SL core.
- I want to thank Jeff Wilcox for his original work on some shims
- ArrayList which I added a ToArray method that takes a type, of course this was ripped off of the ArrayList (via reflector) in the .Net core so someone should let me know if MSFT is going to come take away my computer for publishing this
- I added a ListDictionary which is just a version of the generic Dictionary class with key and value set to type object
- String.Compare(string,string,bool) - a version of string comparison not included in the silverlight core, again thank you reflector
- I made up an ApplicationException as this wasn’t in the SL core
- I made a version of the non generic Comparer class that isn’t in the SL core, thanks reflector
- I added the compiler directive NET_2_0
- A lot of the functionality that was removed was done so by leveraging the SILVERLIGHT compiler directive to exclude the relevant code.
I also went into the framework tests and tweaked a new solution to work with silverlight. I had to modify the tests as follows:
- CanTestContentsOfSortedList excluded - no SortedList in SL
- Remove references and tests with System.Data types (NotGreaterEqualIComparable, NotGreaterIComparable, NotLessEqualIComparable, NotLessIComparable)
- Remove SameColorAs constraint, which was only referenced by NamedAndUnnamedColorsCompareAsEqual, which was commented out anyways
- Remove BinarySerializableTest and XmlSerializableTest tests that depend on Serializable attribute
- Changed DifferentEncodingsOfSameStringAreNotEqual test to use System.Text.Encoding.UTF8.GetString(byte,start,length) overload as (byte) overload isn’t available in SL
- Removed CodeShouldNotCompile and CodeShouldNotCompileAsFinishedConstraint as Microsoft.CSharp.CSharpCodeProvider is not available in SL
So, altogether the changes were minimal and there are 1273 tests passing on the SL version of the framework!
To use these assemblies:
- Setup a SL library as your test library.
- Download the SL libraries here
- Include a reference to the nunit.framework.dll.
- If you have trouble getting tests to run (missing file exceptions to SL assemblies) then set “Copy Local: true” on the appropriate assembly reference in the properties. I always have to do this for the system SL assembly.
If anyone wants more source for what I did or more bits of the nunit framework (like mocks or w/e) ported, please let me know and I will get that done, if possible :) For now I’m happy with just the framework as I use Rhino.Mocks (which already has a SL port) as an isolation container.