返回 IActionResult 的单元测试控制器方法 [英] Unit testing controller methods which return IActionResult

查看:25
本文介绍了返回 IActionResult 的单元测试控制器方法的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在构建 ASP.NET Core WebAPI,我正在尝试为控制器编写单元测试.我发现的大多数示例都来自较旧的 WebAPI/WebAPI2 平台,似乎与新的 Core 控制器无关.

I'm in the process of building an ASP.NET Core WebAPI and I'm attempting to write unit tests for the controllers. Most examples I've found are from the older WebAPI/WebAPI2 platforms and don't seem to correlate with the new Core controllers.

我的控制器方法正在返回 IActionResults.但是,IActionResult 对象只有一个需要控制器上下文的 ExecuteResultAsync() 方法.我正在手动实例化控制器,因此此实例中的控制器上下文为空,这会在调用 ExecuteResultAsync 时导致异常.从本质上讲,这让我走上了一条非常笨拙的道路,以使这些单元测试成功完成并且非常混乱.我想知道必须有一种更简单/更正确的方式来测试 API 控制器.

My controller methods are returning IActionResults. However, the IActionResult object only has a ExecuteResultAsync() method which requires a controller context. I'm instantiating the controller manually, so the controller context in this instance is null, which causes an exception when calling ExecuteResultAsync. Essentially this is leading me down a very hacky path to get these unit tests to successfully complete and is very messy. I'm left wondering that there must be a more simple/correct way of testing API controllers.

另外,我的控制器不会使用 async/await,如果这有区别的话.

Also, my controllers are NOT using async/await if that makes a difference.

我想要实现的简单示例:

Simple example of what I'm trying to achieve:

控制器方法:

[HttpGet(Name = "GetOrdersRoute")]
public IActionResult GetOrders([FromQuery]int page = 0)
{
     try
     {
        var query = _repository.GetAll().ToList();

        int totalCount = query.Count;
        int totalPages = (int)Math.Ceiling((double)totalCount / pageSize) - 1;
        var orders = query.Skip(pageSize * page).Take(pageSize);

        return Ok(new
        {
           TotalCount = totalCount,
           TotalPages = totalPages,

           Orders = orders
        });
     }
     catch (Exception ex)
     {
        return BadRequest(ex);
     }
}

单元测试:

[Fact]
public void GetOrders_WithOrdersInRepo_ReturnsOk()
{
     // arrange
     var controller = new OrdersController(new MockRepository());

     // act
     IActionResult result = controller.GetOrders();

     // assert
     Assert.Equal(HttpStatusCode.OK, ????);
}

推荐答案

假设类似

public IActionResult GetOrders() {
    var orders = repository.All();
    return Ok(orders);
}

在这种情况下,控制器返回一个OkObjectResult 类.

the controller in this case is returning an OkObjectResult class.

将结果转换为您在方法中返回的类型并对其执行断言

Cast the result to the type of what you are returning in the method and perform your assert on that

[Fact]
public void GetOrders_WithOrdersInRepo_ReturnsOk() {
    // arrange
    var controller = new OrdersController(new MockRepository());

    // act
    var result = controller.GetOrders();
    var okResult = result as OkObjectResult;

    // assert
    Assert.IsNotNull(okResult);
    Assert.AreEqual(200, okResult.StatusCode);
}

这篇关于返回 IActionResult 的单元测试控制器方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆