我必须如下测试我的控制器
[HttpGet]
[Route("")]
[HandleError(View= "Error")]
public ActionResult Index(string name)
{
return View("Index", new MyViewModel){
Name = name,
Link = Request.UrlReferrer
}
}
我的ViewModel如下
public class MyViewModel{
public string Name{get;set;}
public Uri Link{get;set}
}
我的问题是,当我编写如下的单元测试时,controller.Index(name)
始终返回null,这似乎是因为我没有模拟ViewModel吗?但是,如何在函数内部模拟ViewModel呢?
我的目的是测试名称是否正确传递给ViewModel,我认为我不应该模拟MyViewModel,对吗?
此外,因为这是HttpGet,我应该模拟Http Request吗?我不确定如何在MVC.NET中测试Http请求
[TestMethod]
public void Index_Return_ViewModel(){
string name = "name";
var controller = new MyController(foo, bar);
var result = controller.Index(name) as ViewResult;
var viewModel = controller.ViewData.Model as MyViewModel;
Assert.AreEqual("Index", result.ViewName);
}
答案 0 :(得分:1)
使用以下示例控制器
public class MyController : Controller {
[HandleError(View = "Error")]
public ActionResult Index(string name) {
return View("Index", new MyViewModel() {
Name = name,
Link = Request.UrlReferrer
});
}
}
为了解释答案。
由于操作访问Request.UrlReferrer
,因此单元测试需要提供必要的依赖关系,以使测试得以完成。
例如
[TestMethod]
public void Index_Return_ViewModel() {
//Arrange
var link = new Uri("http://example.com");
var mockContext = new Mock<ControllerContext>();
mockContext.Setup(_ => _.HttpContext.Request.UrlReferrer)
.Returns(link);
string name = "name";
var controller = new MyController() {
ControllerContext = mockContext.Object
};
//Act
var result = controller.Index(name) as ViewResult;
//Assert
Assert.AreEqual("Index", result.ViewName);
var viewModel = controller.ViewData.Model as MyViewModel;
Assert.IsNotNull(viewModel);
Assert.AreEqual(name, viewModel.Name);
Assert.AreEqual(link, viewModel.Link);
}
无需模拟视图模型。通过将返回的模型属性与期望值进行比较,可以确认该动作的行为符合预期。