Using Rhino Mocks to Unit Test Events on Interfaces, take 2

Phil Haack gives an excellent example of how to test a registration to event while implementing MVP pattern (via Rhino Mocks). If you did not read it yet, take a pause for 2 minutes and give it a look; It is worth it, I promise.


The only thing that bothers me in the example is that the need to assert the triggering of the event kind of spoiled the code. I think that in those scenarios, it’s much better to use some sort of Stub and override the class under test in order to keep the it cleaner. So instead of having this code:


public class Presenter
{
   IView view;
   public Presenter(IView view)
   {
      this.view = view;
      this.view.Load += new EventHandler(view_Load);
   }

   public bool EventLoaded
   {
      get { return this.eventLoaded; }
      set { this.eventLoaded = value; }
   }

   bool eventLoaded;

   void view_Load(object sender, EventArgs e)
   {
      this.eventLoaded = true;
   }
}



I would have created something like this:


public class Presenter
{
   IView view;
   public Presenter(IView view)
   {
      this.view = view;
      this.view.Load += new EventHandler(view_Load);
   }

   protected virtual void view_Load(object sender, EventArgs e)
   {
       // production code here
   }
}


// This will go in the PresenterTests class
public class TestablePresenter : Presenter
{
   public bool WasEventLoaded = false;
   protected override void view_Load(object sender, EventArgs e)
   {
       WasEventLoaded = true;
   }
}



Now we can create an instance of TestablePresenter and Assert the WasEventLoaded field.
My guess is that Phil actually did something like this in his project and merely wanted to show an example, but I still thought it was important enough to demonstrate this separation as I firmly believe we must make sure that our need for tests will not actually hurt the design.

 

Oren Ellenbogen