Xunit测试SerializableError返回对象值

时间:2019-09-29 12:48:37

标签: asp.net-core xunit

我正在用Xunit编写控制器逻辑的单元测试。

我的一个控制器动作返回了一个BadRequestObjectResult对象的ModelStateDictionary

if (!ModelState.IsValid)
{
    return BadRequest(ModelState);
}

为此,我的测试用例添加了如下的ModelState错误:

controller.ModelState.AddModelError("Test", "This is a test model error");

在测试用例的Assert语句中,我正在检查类型为SerializableError的返回对象:

var returnError = Assert.IsType<SerializableError>(objectResult.Value);
Assert.Single(returnError);
Assert.True(returnError.ContainsKey("Test"));
Assert.True(returnError.ContainsValue("This is a test model error"));

Assert.Single(returnError);Assert.True(returnError.ContainsKey("Test"));检查成功通过。

但是,对错误值的检查失败(返回false,但我希望它返回true):

Assert.True(returnError.ContainsValue("This is a test model error"));

从调试中我可以看到Value似乎嵌套在一个额外的string对象中:

enter image description here

但是我无法编写测试该值的测试。我该怎么办?

3 个答案:

答案 0 :(得分:2)

如另一个答案中所述,Dictionary的值是一个数组,因此您应该在断言中解决这个问题。

var returnError = Assert.IsType<SerializableError>(objectResult.Value);

var errors = objectResult.Value as SerializableError;
Assert.Single(errors);
Assert.True(errors.ContainsKey("Test"));

var errorValues = returnError["Test"] as string[];
Assert.Single(errorValues);
Assert.True(errorValues.Single() == "This is a test model error");

由于SerializableError是从Dictionary继承的,因此您应该能够在FluentAssertions库的帮助下以更清晰的方式实现

var expected = new SerializableError
{
    { "Test", new[] {"This is a test model error"}},
};

objectResult.Value.Should().BeOfType<SerializableError>();
objectResult.Value.Should().BeEquivalentTo(expected);

答案 1 :(得分:1)

您的值是一个列表。所以Value [0]或Value.First()。这是一个键值对,因此您应该可以通过returnError [keyName]进行访问。

答案 2 :(得分:1)

您需要将响应转换为 ObjectResult 见下文

var result = response.Result as BadRequestObjectResult

var result = response.Result as OkObjectResult

现在您可以使用 result.Value 属性访问该值