我是单位测试和使用NUnit的MOQ框架的新手。我有一个控制器,它返回一个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);
}
我们如何编写设置方法并执行断言来测试它?感谢
答案 0 :(得分: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);
}
答案 1 :(得分:2)
您所写的测试将随时失败,因为模拟准备不正确。
完整的设置如下:
[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});
}
答案 2 :(得分:1)
有一个名为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>));
}
答案 3 :(得分:0)
上面的实现几乎没有问题,但我认为你会弄清楚(当你输入问题时可能会出现拼写错误)。你提到控制器返回一个ViewModel(ItemViewModel)对象列表和Service返回模型对象列表到控制器(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。