我正在使用 Moq 框架编写单元测试,并且我有一个返回的控制器函数
return Json(new
{
redirectUrl = Url.Action("Action", "Controller"),
isredirection = true
});
我希望能够测试结果,redirectUrl
但不知道如何设置Mock
,Url.Action.
以便我可以指定是否Url.Action("Action", "Controller")
调用返回这个?
我正在使用 Moq 框架编写单元测试,并且我有一个返回的控制器函数
return Json(new
{
redirectUrl = Url.Action("Action", "Controller"),
isredirection = true
});
我希望能够测试结果,redirectUrl
但不知道如何设置Mock
,Url.Action.
以便我可以指定是否Url.Action("Action", "Controller")
调用返回这个?
你不能。关于模拟的规则很容易记住 -不能覆盖,不能模拟1。如果你是从类派生的Url
,你能覆盖Action
方法吗?不可以。Moq、Rhino、FakeItEasy 或任何其他基于 DynamicProxy 的框架也不能。
您的选择范围缩小了以下范围:
包装会是什么样子?
public interface IUrlWrapper
{
string Action(string name, object values);
}
// Wrapper Interface
public class TestedClass
{
private readonly IUrlWrapper url;
public TestedClass(IUrlWrapper urlWrapper)
{
this.url = urlWrapper;
}
// ...
return Json(new
{
redirectUrl = this.url.Action("Action", "Controller"),
isredirection = true
});
// ...
}
通过这样的设置,您可以毫无问题地使用起订量。但是,在单个方法调用中,您也可以在Func
没有任何隔离框架的情况下使用委托:
// Func Delegate
public class TestedClass
{
private readonly Func<string, object, string> urlAction;
public TestedClass(Func<string, object, string> urlAction)
{
this.urlAction = urlAction;
}
// ...
return Json(new
{
redirectUrl = this.urlAction("Action", "Controller"),
isredirection = true
});
// ...
}
在您的测试中,您只需动态创建委托。
1 我写了一篇博文,更详细地介绍了这个问题:How to mock private method with ...