HttpResponseMessage包含所需响应的单元测试

时间:2013-01-31 02:13:15

标签: c# unit-testing asp.net-web-api

我正在编写Web API控制器,现在我有以下代码:

public class PicklistsController : ApiController
{
    private readonly IPicklistRepository _repository;

    public PicklistsController(IPicklistRepository repository)
    {
        _repository = repository;
    }

    public HttpResponseMessage GetPicklistValues(string entityName, string fieldName)
    {
        if(_repository.Exists(entityName, fieldName))
            return Request.CreateResponse(HttpStatusCode.Accepted, _repository.Get(entityName, fieldName));

        return new HttpResponseMessage(HttpStatusCode.NotFound);
    }

}

我正在尝试测试此方法,而我真正想要做的就是验证当存储库找到这些值组合时,HttpResponseMessage包含POCO PicklistItem中的值。作为这个框架的新手,我不太了解HttpResponseMessage的内部工作原理,我在这个网站上发现并通过一般的谷歌搜索告诉我在其内容上使用各种ReadAsync方法,但我真的不想要如果我可以避免它,请使用async。我真的只想验证当我返回时,我填充到我正在返回的对象中的东西是在对象中。这是我到目前为止的单元测试(使用JustMock设置存储库,Target是CUT):

public void Returns_Picklist_Item_JSON_When_Results_Exist()
{
    Repository.Arrange(repo => repo.Exists(EntityName, FieldName)).Returns(true);

    const int value = 2;
    const string label = "asdf";
    var mynewPicklistItem = new PicklistItem() { Label = label, Value = value };
    Repository.Arrange(repo => repo.Get(EntityName, FieldName)).Returns(Enumerable.Repeat<PicklistItem>(mynewPicklistItem, 1));

    var response = Target.GetPicklistValues(EntityName, FieldName);
    //Assert.IsTrue(I don't know what to do here -- suggestions appreciated);
}

断言的任何想法?或者我咆哮错误的树/从根本上误解了这应该如何工作?感谢...

2 个答案:

答案 0 :(得分:18)

我正在使用Web API 2.1,并且有一个名为TryGetContentValue的函数:

[Test]
public void TheTestMethod()
{
    // arrange

    var ctrl = new MyController();

    ctrl.Request = Substitute.For<HttpRequestMessage>();  // using nSubstitute
    ctrl.Configuration = Substitute.For<HttpConfiguration>();

    // act

    HttpResponseMessage result = ctrl.Get();

    MyResponse typedresult;
    result.TryGetContentValue(out typedresult);     // <= this one

    // assert
}

答案 1 :(得分:16)

如果Content是对象,请尝试将其转换为ObjectContent - Value属性应包含您的对象。

如果它是StreamContent,那么我不知道其他方式而不是ReadAsAsync。您仍然可以阻止任务的结果以查看响应。

以下是一个例子:

var response = Target.GetPicklistValues(EntityName, FieldName);
ObjectContent objContent = response.Content as ObjectContent;
PicklistItem picklistItem = objContent.Value as PicklistItem;