如何编写单元测试来检查返回的项目是否属于列表类型

how to write a unit test to check returned items are of type list

我不熟悉单元测试和将 MOQ 框架与 NUnit 结合使用。我有一个控制器,其中 returns ViewModel 对象列表为

public ActionResult ValidateOutstandingItems()
{
        var entities = _itemsService.GetAll(true).Where(x => x.IsValid == null);
        var model = entities.Select(e => _mappingEngine.Map<ItemModel>(e));
        return View(model);
}

我需要编写一个单元测试来检查此操作方法返回的项目是否属于 List<ItemModel>

类型

我写过这样的东西

[Test]
    public void ValidateOutstandingItemsReturnsItemsViewModelList()
    {            
        var itemsService = new Mock<ItemsService>();
        var mapper = new Mock<IMappingEngine>();
        var itemsList = new List<itemModel>()
        {
            new itemModel{Id = 1,Name = "item 1"},
            new itemModel(){Id=2,Name="item 2"}

        };

        var controller = new ItemController(itemsService.Object, mapper.Object);
        // Act
        var result = controller.ValidateItems();

        // Assert
        var model = ((ViewResult)result).Model as List<ItemModel>;
        Assert.True(model.Count == 2);

    }

我们如何编写设置方法并进行断言来测试它?谢谢

一种方法是在使用 as List<ItemModel> 强制转换后检查您的模型对象是否为空。如果类型不是 List<ItemModel>,则在该语句后将为 null。

[Test]
public void ValidateOutstandingItemsReturnsItemsViewModelList()
{            
    var itemsService = new Mock<ItemsService>();
    var mapper = new Mock<IMappingEngine>();
    var itemsList = new List<itemModel>()
    {
        new itemModel{Id = 1,Name = "item 1"},
        new itemModel(){Id=2,Name="item 2"}

    };

    var controller = new ItemController(itemsService.Object, mapper.Object);
    // Act
    var result = controller.ValidateItems();

    // Assert
    var model = ((ViewResult)result).Model as List<ItemModel>;

    // Test whether type is List<ItemModel>
    Assert.IsNotNull(model, "model is not of type List<ItemModel>");
    Assert.True(model.Count == 2);

}

你上面的实现没有什么问题,但我想你会弄明白的(当你输入问题时可能是拼写错误)。您提到了控制器 return ViewModel (ItemViewModel) 对象的列表和服务 return 控制器 (ItemModel) 的模型对象列表,说过要设置模拟对象,您可以尝试类似的方法:

        // Setup itemService GetAll like this
        itemsService.Setup(m => m.GetAll(It.Is(true))).Returns(itemsList.ToArray());

        mapper.Setup(m => m.Map<ItemModel[], ItemViewModel[]>(It.IsAny<ItemModel[]>()))
            .Returns(itemViewModelList.ToArray());

断言:

        // Act
        var result = controller.ValidateOutstandingItems() as ViewResult;

        // Check number of items are correct
        var model = result.Model as List<ItemViewModel>;
        Assert.True(model.Count == 2);

您必须在单元测试中创建 itemList 和 itemViewModelList。

有一个名为 IsInstanceOfType 的方法

[Test]
public void ValidateOutstandingItemsReturnsItemsViewModelList()
{            
    var itemsService = new Mock<ItemsService>();
    var mapper = new Mock<IMappingEngine>();
    var itemsList = new List<itemModel>()
    {
        new itemModel{Id = 1,Name = "item 1"},
        new itemModel(){Id=2,Name="item 2"}

    };

    var controller = new ItemController(itemsService.Object, mapper.Object);
    // Act
    var result = controller.ValidateItems();

    // Assert
    Assert.IsInstanceOfType(((ViewResult)result).Model, typeof(List<ItemModel>));

}

您编写的测试随时都会失败,因为模拟没有正确准备。

完整的设置如下所示:

[Test]
public void ValidateOutstandingItemsReturnsItemsViewModelList()
{            
    var itemsService = new Mock<ItemsService>();
    var mapper = new Mock<IMappingEngine>();
    var itemsList = new List<itemModel>()
    {
        new itemModel{Id = 1,Name = "item 1"},
        new itemModel(){Id=2,Name="item 2"}
    };
    itemsService.Setup(s=>s.GetAll(true)).Returns(itemsList);

    var mapped1 = new ItemModel();
    var mapped2 = new ItemModel();

    mapper.Setup(m=>m.Map<ItemModel>(itemList[0])).Returns(mapped1);
    mapper.Setup(m=>m.Map<ItemModel>(itemList[1])).Returns(mapped2);

    var controller = new ItemController(itemsService.Object, mapper.Object);
    // Act
    var result = controller.ValidateItems();

    // Assert
    var model = ((ViewResult)result).Model as List<ItemModel>;
    //Verify that the model contains the 2 mapped elements
    CollectionAssert.AreEqual(model, new[]{mapped1, mapped2});
}