Wednesday, October 17, 2012

Testing REST clients

Problem

While writing code for Resty.Net I had a problem about how should I deal with the tests. Well I could easily write tests for most of the parts but, I got stock at writing test for the RestRequest class. I thought I could mock RestRequest with a fake implementation. But mocking wouldn't be a solution for my situation. Mocking would have been the perfect solution if I was using Resty.Net in another project, and testing that project. As I'm trying to test if RestRequest itself is implemented correctly or not, mocking RestRequest wasn't the solution.

I thought about mocking the underlying HttpWebRequest, but wasn't quite satisfied with it too.

Search for solution

I did what most of person in the above situation would usually do, I "Googled". After googling for sometimes, changing my keyword combinations and scanning through many pages I finally found a good enough solution at CSharp On The Fritz. Here is the link to the exact post I'm talking about: http://www.csharpfritz.com/post/26765731081/restful-client-unit-testing-with-nancyfx. Yeah, it suggests a neat idea of using embedded NancyFx server and making requests against that server.

The solution

Once I got the inspiring idea of using NancyFx for testing, I did what most of the lazy coders would do, i.e I copied the code at http://www.csharpfritz.com/post/26765731081/restful-client-unit-testing-with-nancyfx, and began writing tests. All went quite well for sometime, then as the number of tests increased the tests began to fail. The problem was, the port sometimes didn't get released by a previous tests, while the new test was already running. Now, I had to make changes to the basic code that I had CTRL+Ced and CTRL+Ved.

Here's my solution:

public class NancyHostHelper
{
 protected Uri _uri = new Uri("http://localhost:50001");
 private NancyHost _Nancy;
 private static int port = 50001;

 public Uri Start()
 {
  bool nancyStarted = false;
  // Need to retry in order to ensure that we properly startup after any failures
  for (var i = 0; i < 3; i++)
  {
   _Nancy = new NancyHost(_uri);

   try
   {
    _Nancy.Start();
    nancyStarted = true;
    break;
   }
   catch (HttpListenerException)
   {
    UriBuilder ub = new UriBuilder(_uri);
    ub.Port = ++port;
    _uri = ub.Uri;
   }
   catch
   {
    try
    {
     _Nancy.Stop();
    }
    catch (Exception e)
    {
    }
   }
  }

  if (!nancyStarted)
  {
   //Don't allow to run the tests if Nancy not started.
   throw new Exception();
  }

  return _uri;
 }

 public void Stop()
 {
  try
  {
   _Nancy.Stop();
   _Nancy = null;
  }
  catch { }
 }
}
Well the solution as you can see above is:
  • Increment the port number and,
  • Try restarting the server again, at new incremented port number.

You, can see the practical usage of the above class in the github repository for Resty.Net at https://github.com/nripendra/Resty.Net/blob/master/tests/Resty.Net.Tests/RestRequestTest.cs.

So far its working quite well, I'll keep updating this blog if anything comes up that makes it necessary to make other changes to the above code.

1 comment:

  1. updated link
    http://www.jeffreyfritz.com/2012/07/restful-client-unit-testing-with-nancyfx/

    ReplyDelete