Jim Geurts
Jim Geurts

Reputation: 20429

How do I unit test controllers for an asp.net mvc site that uses StructureMap and NHibernate?

I have an asp.net mvc2 application that is using StructureMap 2.6 and NHibernate 3.x. I would like to add unit tests to the application but am sort of at a loss for how to accomplish it.

Say I have a basic controller called Posts that has an action called Index. The controller looks something like:

public class PostsController : Controller {

  private readonly IPostService _postService;
  public PostsController(IPostService postService) {
    _postService = postService;
  }

  public ActionResult Index() {
    return View(_postService.QueryOver<Post>().Future());
  }
}

If I wanted to create an nunit test that would verify that the index action is returning all of the posts, how do I go about that? If mocking is recommended, do you just assume that interaction with the database will work?

Sorry for asking such a broad question, but my web searches haven't turned up anything decent for how to unit test asp.net mvc actions that use StructureMap (or any other IOC) and NHibernate.

btw, if you don't like that I return a QueryOver object from my post service, pretend it is an IQueryable object. I'm using it essentially in the same way.

Upvotes: 1

Views: 631

Answers (2)

Pedro
Pedro

Reputation: 2310

To unit test your controller action you must mock your service, as it is a external process that are beyond the scope of the unit being tested.

But no, you don't have to assume that your service will just work. You should write integration tests that will ensure that your service works properly.

The unit test will give you coverage on the behavior of the Controller and the integration test on the behavior of the service. Once you got both covered you are fine.

Upvotes: 0

Ryan
Ryan

Reputation: 4313

I would refactor your query into the service layer itself. My reason for suggesting this is that you can then have all your security, projections, paging, filtering, etc in one spot. Even if you don't have these concerns now, it will be much easier to add them in later if everything is not strewn about in different controller actions.

With this split up you can easily unit test the GetAllPosts() method. (Either mock out your repo or just plug into an in memory database.) As far as testing the controller action, it's basically a service call at this point so would you gain any benefit from testing it? In my opinion, probably not.

// service
public IQueryable<Post> GetAllPosts()
{
   return postRepository.QueryOver<Post>().Future();
}

// controller public ActionResult Index() { return View(_postService.GetAllPosts()); }

Upvotes: 1

Related Questions