skip to the main content area of this page
Patterns and Practices

MVP Bundle Could Use Mock Framework and Service Locator Guidance


The MVP Bundle in the Web Client Software Factory v2.0 offers guidance on the Model-View-Presenter Pattern in your asp.net applications. It has a nice overview and comparison of Supervising Controller and Passive View MVP, View-Presenter Communications using delegation and event-based approaches, as well as using mocks for testing. Given this bundle is more focused on educating the customer on the MVP Pattern as opposed to WCSF implementations, I would love to see guidance on the use of Mock Frameworks as opposed to hand coded mocks. Here are some thoughts on the use of Rhino Mocks as well as a Service Locator using the quickstart example in the MVP Bundle.

 

Mock Frameworks

For example, hand created mocks seem to be a thing of the past. Most tests these days make use of mock frameworks where appropriate. All testing related guidance from Microsoft Patterns & Practices comes with hand created mocks, but no guidance on the use of mock frameworks. This would seem contrary to the goal of Microsoft Patterns & Practices to keep us up-to-date on proven practices. P&P can provide us mock framework guidance and examples without endorsing a particular framework, and I think the guidance would be invaluable.

For example, the ContactsListPresenterTestFixture in the MVP Bundle has a test, called ControllerPropertyReturnsInjectedController, that makes use of a couple of handcoded mocks that could easily be replaced with Rhino Mocks with a lot less test code:

 

[Test]

public void ControllerPropertyReturnsInjectedController()

{

    MockRepository mocks = new MockRepository();

    IContactsController controller = mocks.CreateMock<IContactsController>();

    IContactsListView view = mocks.CreateMock<IContactsListView>();

    ContactsListPresenter presenter = new ContactsListPresenter(view, controller);

    Assert.AreSame(controller, presenter.Controller);

}

 

Personally, I don't care which tool p&p uses to illustrate the use of a mock framework as part of testing proven practices, and I certainly won't take their choice as any endorsement. However, I feel that developers will be more apt to write tests and use mocks if they could understood the value of a productive mock framework with examples. I also feel that neglecting to show examples of a mock framework keeps developers in the dark about such tools.

 

Service Locator

One bit of code in the MVP Bundle quickstart that concerns me a bit is as follows:

 

public partial class ContactsList : Page, IContactsListView

{

    private ContactsListPresenter _presenter;

 

    protected void Page_Load(object sender, EventArgs e)

    {

        //Since we are not using CWAB we need to wire the MVP pattern manually

        _presenter = new

            ContactsListPresenter(this, new ContactsController(new CustomersDataSource()));

 

        //...

    }

 

    //...

}

 

Notice that the view in this case explicitly provides the CustomersDataSource dependency for the ContactsController. Even if not using an IoC Tool this would not be considered a good practice as the view should not be responsible for handling this wiring as well as choosing the appropriate datasource. This is a maintenance nightmare waiting to happen.

A better solution would be to use a simple Service Locator and a ContactsListPresenter Constructor that requests the service from a Service Locator:

 

public class ContactsListPresenter

{

    private IContactsListView _view;

    private IContactsController _controller;

 

    public ContactsListPresenter(IContactsListView view)

        :this(view, ServiceLocator.Get<IContactsController>()) {}

 

    public ContactsListPresenter(IContactsListView view,

                                IContactsController controller)

    {

        _view = view;

        _controller = controller;

    }

 

     // ...

}

 

and have the view hook into the presenter as such:

 

public partial class ContactsList : Page, IContactsListView

{

    private ContactsListPresenter _presenter;

 

    protected void Page_Load(object sender, EventArgs e)

    {

        _presenter = new ContactsListPresenter(this);

 

        //...

    }

 

    //...

}

 

In your service locator you can then at the very least do something similar to:

 

return new ContactsController(new CustomersDataSource());

 

in response to a request for IContactsController. Personally I would probably have a separate call in a ContactsController Default Constructor that did another Service Locator call like ServiceLocator.Get<ICustomersDataSource>() to get the CustomersDataSource and so on and so forth. This is when a good IoC tool becomes handy.

You can obviously play with this to your liking, but doing the wiring in the view would be a worst practice in my opinion as it exposes too many details about how objects and services are constructed as well as their dependencies and will lead to a maintenance nightmare if you change the way the objects and services are created later.

The Service Locator Design Pattern solves this problem nicely and does not require any external tools.

 

Conclusion

Overall, the MVP Bundle is wonderful and I love the guidance provided by Microsoft Patterns & Practices. In general, however, I wish they would not avoid guidance in areas for which they don't have tools, because I think it lessens the value of the guidance. They need to find a way to offer more well-rounded guidance without endorsing a tool.


Tags: MVPBundle, RhinoMocks, GuidanceBundles, ModelViewPresenter, SupervisingController, PassiveView


Topics



Popular Tags



Recent Links