测试使用 User.Identity.Name 的控制器操作

发布于 2024-08-04 12:04:12 字数 473 浏览 3 评论 0原文

我有一个依赖 User.Identity.Name 来获取当前用户的用户名来获取他的订单列表的操作:

public ActionResult XLineas()
    {
        ViewData["Filtre"] = _options.Filtre;
        ViewData["NomesPendents"] = _options.NomesPendents;
        return View(_repository.ObteLiniesPedido(User.Identity.Name,_options.Filtre,_options.NomesPendents));
    }

现在我正在尝试为此编写单元测试,但我陷入了如何提供 Mock 的困境对于用户.身份.名称。如果我按照我的方式运行测试(没有用户的模拟...),我会得到一个 Null.. 异常。

哪种方法是正确的?我认为我的操作代码不适合单元测试。

I have an action that relies on User.Identity.Name to get the username of the current user to get a list of his orders:

public ActionResult XLineas()
    {
        ViewData["Filtre"] = _options.Filtre;
        ViewData["NomesPendents"] = _options.NomesPendents;
        return View(_repository.ObteLiniesPedido(User.Identity.Name,_options.Filtre,_options.NomesPendents));
    }

Now I'm trying to write unit tests for this, but I get stuck on how to provide a Mock for User.Identity.Name. If I run my test as I have it (without mock for User...), I get a Null.. exception.

Which is the correct approach for this? I'm thinking that my Action code is not good for unit testing.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

上课铃就是安魂曲 2024-08-11 12:04:12

您可以使用此代码

public SomeController CreateControllerForUser(string userName) 
{
    var mock = new Mock<ControllerContext>();
    mock.SetupGet(p => p.HttpContext.User.Identity.Name).Returns(userName);
    mock.SetupGet(p => p.HttpContext.Request.IsAuthenticated).Returns(true);

    var controller = new SomeController();
    controller.ControllerContext = mock.Object;

    return controller;
}

它使用 Moq 模拟框架,但确保您可以使用任何您喜欢的东西。

You can use this code

public SomeController CreateControllerForUser(string userName) 
{
    var mock = new Mock<ControllerContext>();
    mock.SetupGet(p => p.HttpContext.User.Identity.Name).Returns(userName);
    mock.SetupGet(p => p.HttpContext.Request.IsAuthenticated).Returns(true);

    var controller = new SomeController();
    controller.ControllerContext = mock.Object;

    return controller;
}

It uses Moq mocking framework, but sure you can use anything you like.

別甾虛僞 2024-08-11 12:04:12

更好的方法是传递一个 string 参数 userName (或一个 IPrincipal 参数 user,如果您需要的信息不仅仅是名称)到 ActionMethod,您可以使用 ActionFilterAttribute 将其“注入”到正常请求中。当您测试它时,您只需提供自己的模拟对象,因为操作过滤器的代码将不会运行(在大多数情况下 - 如果您特别想要的话,有很多方法可以...)

Kazi Manzur Ra​​shid 在第 7 点下详细描述了这一点在 优秀的博客文章

A better way of doing this would be to pass a string argument userName (or an IPrincipal argument user, if you need more information than just the name) to the ActionMethod, which you "inject" in a normal request using an ActionFilterAttribute. When you test it, you just supply your own mock object, as the action filter's code will not run (in most cases - there are ways to, if you specifically want to...)

Kazi Manzur Rashid describes this in detail under point 7 in an excellent blog post.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文