如何在不使用字面数字的情况下测试 ASP.NET 控制器响应状态码的值?

huangapple go评论67阅读模式
英文:

How can I test the value of ASP.NET Controller response status codes without using their literal number?

问题

我注意到 ASP.NET Core 控制器在返回请求的状态代码时,可以使用 NotFound() 表示 404,或者 Ok() 表示 200,这些都是 StatusCodeResult 对象。下面是一个示例控制器函数:

public ActionResult<MyItem> GetItemById(int ItemId) {
    var item = _service.GetItemById(ItemId);
    if (item is null) {
        return NotFound();
    }
    return item;
}

当我为这个控制器的 GetItemById 函数编写单元测试时,我想测试如果没有具有该 ItemId 的项目时,它是否返回 404。我目前编写以下单元测试(在这个示例中,我使用 xUnit):

[Fact]
public void TestGetItemByIdNotFound() {
    var response = controller.GetItemById(1); // 没有 ItemId 为 1 的项目
    var result = Assert.IsType<NotFoundResult>(response);
    Assert.Equal(404, result!.StatusCode);
}

在我的测试中,我将整数 404 与结果的状态代码进行比较。我更希望在我的测试中引用类似于 NotFound() 的东西,而不是一个数字,这样我就不必记住控制器将返回的每个 StatusCodeResult 的状态代码,只需在断言中使用类似语法的东西。是否有一种方法可以实现这样的效果?

到目前为止,我只是创建了不同状态代码及其返回值的枚举,然后在我的测试中引用它们:

enum StatusCodes {
    Ok = 200,
    NotFound = 404,
    // ...
}

// ...

Assert.Equal((int)StatusCodes.NotFound, result!.StatusCode);

但我想知道是否有一种更简洁的方法,可以让我不必枚举每个可能的状态代码。

英文:

I noticed that ASP.NET Core controllers, when returning status codes for requests, can return NotFound() for a 404, or Ok() for a 200, which are StatusCodeResult objects. Here's an example controller function that does so:

public ActionResult&lt;MyItem&gt; GetItemById(int ItemId) {
    var item = _service.GetItemById(ItemId);
    if (item is null) {
        return NotFound();
    }
    return item;
}

When I write a unit test for this controller's GetItemById function, and I want to test if it returns a 404 when there is no item with that ItemId, I currently write the following unit test (I'm using xUnit in this example):

[Fact]
public void TestGetItemByIdNotFound() {
    var response = controller.GetItemById(1); // no item with ItemId 1
    var result = Assert.IsType&lt;NotFoundResult&gt;(response);
    Assert.Equal(404,result!.StatusCode);
}

In my test, I'm comparing the integer 404 with the status code of the result. I would prefer to reference something similar to NotFound() instead of a number in my test so that I don't have to memorize the status code for every StatusCodeResult that my controller will return, and just have something with similar syntax in my assertion. Is there a way to do so?

So far, I've just made an enumerator of different status codes and their returns, then referenced those in my test:

enum StatusCodes {
    Ok = 200,
    NotFound = 404,
    ...
}

...

Assert.Equal((int)StatusCodes.NotFound, result!.StatusCode)

But I'm curious if there's a cleaner way that leaves me without having to enumerate every possible status code.

答案1

得分: 1

如果未找到该项。 对于这种情况,单元测试只需检查返回类型是否为 NotFoundResult,无需手动检查状态代码,因为我们已经检查了类型,从而确保状态代码将为 404。

此外,正如 @Martin 提到的,状态代码已经在 System.Net.HttpStatusCode 中定义。

英文:

if the Item is not found. For this case, the unit test just checks if the return type is NotFoundResult, you don't need to manually check for the status code because we already check the type which ensures that status code will be 404.

moreover like @Martin mention status codes already defined in System.Net.HttpStatusCode

huangapple
  • 本文由 发表于 2023年5月29日 01:20:37
  • 转载请务必保留本文链接:https://go.coder-hub.com/76352691.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定