asp.net mvc如何正确测试控制器

lan*_*der 5 asp.net-mvc unit-testing mocking

我在测试控制器时遇到了困难.原来我的测试控制器看起来像这样:

SomethingController CreateSomethingController()
{
    var somethingData = FakeSomethingData.CreateFakeData();
    var fakeRepository = FakeRepository.Create();

    var controller = new SomethingController(fakeRepository);

    return controller;
}
Run Code Online (Sandbox Code Playgroud)

这对于大多数测试都很好,直到我得到了Request.IsAjaxRequest()代码的一部分.所以我不得不模拟HttpContext和HttpRequestBase.所以我的代码然后改为看起来像:

public class FakeHttpContext : HttpContextBase
{
    bool _isAjaxRequest;

    public FakeHttpContext( bool isAjaxRequest = false )
    {
        _isAjaxRequest = isAjaxRequest;
    }

    public override HttpRequestBase Request
    {
        get
        {
            string ajaxRequestHeader = "";

            if ( _isAjaxRequest )
                ajaxRequestHeader = "XMLHttpRequest";

            var request = new Mock<HttpRequestBase>();
            request.SetupGet( x => x.Headers ).Returns( new WebHeaderCollection 
            {
                {"X-Requested-With", ajaxRequestHeader} 
            } );

            request.SetupGet( x => x["X-Requested-With"] ).Returns( ajaxRequestHeader );

            return request.Object;
        }
    }

    private IPrincipal _user;

    public override IPrincipal User
    {
        get
        {
            if ( _user == null )
            {
                _user = new FakePrincipal();
            }
            return _user;
        }
        set
        {
            _user = value;
        }
    }
}


SomethingController CreateSomethingController()
{
    var somethingData = FakeSomethingData.CreateFakeData();
    var fakeRepository = FakeRepository.Create();

    var controller = new SomethingController(fakeRepository);

    ControllerContext controllerContext = new ControllerContext( new FakeHttpContext( isAjaxRequest ), new RouteData(), controller );
     controller.ControllerContext = controllerContext;

    return controller;
}
Run Code Online (Sandbox Code Playgroud)

现在它进入我调用的控制器中的那个阶段Url.Route并且Url为空.所以看起来我需要开始为我的控制器模拟路线.

我似乎花了更多的时间在Google上搜索伪造/模拟对象,然后调试以确保我的假货是正确的,而不是实际编写测试代码.有没有更简单的方法来测试控制器?我看过MvcContrib的TestControllerBuilder,它可以解决一些问题,但似乎并没有做任何事情.有没有其他可用的工作,让我专注于编写测试而不是编写模拟?

谢谢

ant*_*res 1

您可以使用一些库来为您提供一些开箱即用的对象。例如RhinoMock、 NMock ...等。我个人使用Moq - 它足够好而且免费。Moq 中我最喜欢的是 linq 表达式。