模拟HttpContext不起作用

Vol*_*zun 10 asp.net asp.net-mvc unit-testing rhino-mocks mocking

我试图模拟HttpContext,以便我可以单元测试我的控制器的Request.IsAuthenicated调用.我正在使用我在Scott Hanselman博客上发现代码来使用rhino.mocks模拟HttpContext.所以我有这个单元测试件:

PostsController postsController = new PostsController(postDL);
mocks.SetFakeControllerContext(postsController);
Expect.Call(postsController.Request.IsAuthenticated).Return(true);
Run Code Online (Sandbox Code Playgroud)

在我的控制器操作中,我有类似的事情, if(Request.IsAuthenticated).... 当我尝试运行单元测试时,测试失败抛出空异常,当我尝试调试单元测试时,我看到HttpContext从未分配给控制器.有任何想法吗?

Tim*_*ott 8

这应该工作:

PostsController postsController = new PostsController(postDL);
var context = mocks.Stub<HttpContextBase>();
var request = mocks.Stub<HttpRequestBase>();
SetupResult.For(request.IsAuthenticated).Return(true);
SetupResult.For(context.Request).Return(request);    
postsController.ControllerContext = new ControllerContext(context, new RouteData(), postsController);
Run Code Online (Sandbox Code Playgroud)


Rob*_*per 0

现在,为了披露,我还没有亲手接触您正在使用的大部分内容,但是:

如果您想模拟 IsAuthenticated,为什么不直接创建一个静态类来返回一个可由测试代码操作的 bool 值呢?

这有点粗糙,但希望你能明白:

interface IAuthenticationChecker
{
    bool IsAuthenticated { get; }
}

public class MockAuthenticationChecker : IAuthenticationChecker
{
    static bool _authenticated = false;

    public static void SetAuthenticated(bool value)
    {
        _authenticated = value;
    }
    #region IAuthenticationChecker Members

    public bool IsAuthenticated
    {
        get { return _authenticated; }
    }

    #endregion
}

public class RequestAuthenticationChecker : IAuthenticationChecker
{

    #region IAuthenticationChecker Members

    public bool IsAuthenticated
    {
        get {
            if (HttpContext.Current == null)
                throw new ApplicationException(
                    "Unable to Retrieve IsAuthenticated for Request becuse there is no current HttpContext.");

            return HttpContext.Current.Request.IsAuthenticated;
        }
    }

    #endregion
}
Run Code Online (Sandbox Code Playgroud)

然后,您可以在应用程序级别使用对其中任何一个的引用,是的,这意味着您必须在应用程序级别添加引用,并且您需要使用不同的引用而不是请求,但您还可以完全控制测试的身份验证:)

仅供参考 - 这完全可以被炸散,我在大约一分钟内把它拼凑在一起:)