使用authorize属性对控制器进行单元测试匿名用户

时间:2014-06-08 23:48:09

标签: unit-testing asp.net-mvc-5

我正在尝试构建一个单元测试,以确保未经身份验证的用户无法访问控制器。当我运行测试时,用户被发现是经过身份验证的。我如何模拟,以便测试发现被模拟的用户是未经身份验证的。

我正在使用带有indentity 2.0的mvc5

控制器

[Authorize]
public class ProfileController : Controller
{
    private ICompanyServiceLayer _service;

    public ProfileController(ICompanyServiceLayer service)
    {
        _service = service;
    }

    public ActionResult Index(int id)
    {
            /* cool stuff happens here */
        return View();
    }
}

测试

[Test]
public void Index_As_Annonymous_User()
{
    // arrange
    Mock<ICompanyServiceLayer> service = new Mock<ICompanyServiceLayer>();

    GenericIdentity id = new GenericIdentity("");
    Mock<IPrincipal> princ = new Mock<IPrincipal>();
    princ.Setup(x => x.Identity).Returns(id);


    Mock<HttpContextBase> contextBase = new Mock<HttpContextBase>();
    contextBase.Setup(x => x.User).Returns(princ.Object);

    Mock<ControllerContext> controllerContext = new Mock<ControllerContext>();
    controllerContext.Setup(x => x.HttpContext).Returns(contextBase.Object);

    // controller            
    ProfileController controller = new ProfileController(service.Object);
    controller.ControllerContext = controllerContext.Object;

    // act
    var result = controller.Index(1);

    // assert
    Assert.IsInstanceOf(typeof(HttpStatusCodeResult), result);
}

根据blorkfish建议进行更新

[Test]
public void Index_As_Annonymous_User()
{
    // arrange
    Mock<ICompanyServiceLayer> service = new Mock<ICompanyServiceLayer>();

    Mock<HttpRequestBase> request = new Mock<HttpRequestBase>();
    request.Setup(x => x.IsAuthenticated).Returns(false);

    Mock<HttpContextBase> contextBase = new Mock<HttpContextBase>();
    contextBase.Setup(x => x.Request).Returns(request.Object);

    // controller            
    ProfileController controller = new ProfileController(service.Object);
    controller.ControllerContext = new ControllerContext(contextBase.Object, new RouteData(), controller);

    // act
    var result = controller.Index(1);

    // assert
    Assert.IsInstanceOf(typeof(HttpStatusCodeResult), result);
}

2 个答案:

答案 0 :(得分:0)

使用Moq,您需要模拟HttpContextBase并确保其IsAuthenticated属性返回false。

   var mockHttpContext = new Mock<HttpContextBase>();

        mockHttpContext.SetupGet(c => c.User.Identity.IsAuthenticated).Returns(false);

        var mockControllerContext = new Mock<ControllerContext>();

        mockControllerContext.Setup(c => c.HttpContext).Returns(mockHttpContext.Object);

        controller.ControllerContext = mockControllerContext.Object;

然后,在控制器操作中运行以下命令应该返回false:

User.Identity.IsAuthenticated

答案 1 :(得分:-1)

mvc框架检查HttpRequest.IsAuthenticated标志。要模拟这个,你需要模拟httpContext和httpRequest:

var httpContext = MockRepository.GenerateMock<HttpContextBase>();
var httpRequest = MockRepository.GenerateMock<HttpRequestBase>();

httpContext.Stub(x => x.Request).Return(httpRequest);
httpRequest.Stub(x => x.IsAuthenticated).Return(false);

UserController controller = new UserController();
controller.ControllerContext 
    = new ControllerContext(httpContext, new RouteData(), controller);