How to test generic methods using Microsoft.Fakes

9 באוגוסט 2012

תגובה אחת

I have started using the Microsoft.Fakes, one of the new testing future in VS2012, some time ago and I found this tool to be very very powerful and many of my new test are written with the help of Stubs and Shims. If you don’t know what I am talking about you can read about Stubs in here, about Shims in here and you can watch the a very good lecture about it (and more new futures on testing in VS2012) in here.

At some point I wanted to detour using Shims a generic method, but I couldn’t find a good solution for it. After digging a bit I have successfully managed to do it and here is how:

Lets say I have a generic method that do something in a class that do something

public class DoSomthingClass
{
    public T DoSomething<T>(T val)
    {
        return val;
    }
}

This method doesn’t really do much, only return the entered value. Now lets say I got another method, DoSomething2 that uses the method DoSomething<T> with type ‘int’:

public int DoSomething2 (int val1, int val2)
{
    return val2 + DoSomething<int>(val1);
}

Now, I would like to create tests for method DoSomething2, but I would like to detour method DoSomthing<T>, I don’t want to test method DoSomething<T>, I only want to test the logic of method DoSomething2 (even though in this method is quite simple). I would like to isolate the logic of method DoSomething2 and create a Shim for DoSomthing<T>.

In order to to that, first of course I will have to create a test class, and a test method. Now I would have to use a Shim to mimic the call to DoSomething<int> inside method DoSomething2. To do that for a generic method I will have to create a delegate and use Microsort FakesDelegates library.

Here is the full test :

[TestMethod]
public void DoSomething2_test()
{
    using (ShimsContext.Create())
    {
        Func<BL.DoSomthingClass, int, int> myDelegate = 
            delegate(BL.DoSomthingClass doSomthingClass, int val)
        {
            return 8;
        };

        ShimDoSomthingClass.AllInstances.DoSomethingOf1M0<int>
            (new FakesDelegates.Func<BL.DoSomthingClass, int, int>(myDelegate));
        var doSomthingInstance = new DoSomthingClass();

        Assert.IsTrue(doSomthingInstance.DoSomething2(1, 2) == 10);
    }
}

As you can see, I have a fake delegate that gets DoSomthingClass and val and return the value 8 (a dummy value), and I am creating a new FakesDelegates.Func that gets my delegate. As you can see, when I execute this test my delegate will be executed and the result of the code : doSomthingInstance.DoSomething2(1, 2) will be 10 and not 3 as expected, and my test will pass.

Hope this code helps all of you writing tests, keep it up it will make your code better.

הוסף תגובה
facebook linkedin twitter email

כתיבת תגובה

האימייל לא יוצג באתר. שדות החובה מסומנים *

תגובה אחת

  1. Joe12 בפברואר 2013 ב 12:29

    That helped, thanks a lot.

    הגב