我只是设置了一些第一次单元测试,我无法完全看到我是如何实现的(使用我当前的测试结构)可以完成,这意味着我不确定我的方法是否正确测试不正确,或者只是对xUnit的限制。
我正在测试我的MVC Controllers
,并希望确保它们都提供ArgumentNullException
如果它们被构造为传递null作为参数(它们通过现实世界中的Castle解析)
所以,我在Test类上有一个私有字段:
private IEnumerable<Type> ControllerTypes = typeof(MyBaseController).Assembly.GetTypes().Where(t => IsController(t));
然后,我的测试方法:
[Fact]
public void EnsureControllersThrowIfProvidedWithNull() {
foreach (var controller in ControllerTypes) {
var ctrs = GetConstructorsForType(controller);
if (null == ctrs || !ctrs.Any()) { //if the controller has no constructors, that's fine, we just skip over it
continue;
}
var ctr = ctrs.ElementAt(0);
var ctrParamsAsNull = ctr.GetParameters().Select(p => (object)null);
Assert.Throws<ArgumentNullException>(() => {
ctr.Invoke(ctrParamsAsNull.ToArray());
});
}
}
所以这一切都运行正常,我运行了测试运行器,并且我的一个Controllers
在传递null时没有抛出ArgumentNullException
,很棒,我的测试失败了,但是我没有从给定的输出中知道它是哪个控制器。
我知道如何通过测试调试以查看哪个失败,并且可以手动遍历我的所有控制器以检查它是哪个,但知道哪个控制器失败会很有用。 / p>
或者我只是在这里使用单元测试错了?
(旁注,还有另一个测试可以确保每个控制器只有一个公共构造函数,因此只要第一个测试通过,我就可以确定在触发时我会定位正确的构造函数。)
由于
注意:
测试的逻辑有一个缺陷,这意味着它没有完全覆盖我期望它的内容,只要它为至少一个参数抛出ArgumentNullException
,那么它将通过测试,这是不对的。但是由于参数是接口,我无法实例化它们的新实例。所以任何想要复制测试代码的人都不会这样做。这里没有寻找解决这个问题的方法。
答案 0 :(得分:2)
Assert.Throws只是在try catch块中执行委托的辅助方法。您不必使用它,您可以用自己的实现替换它。类似的东西:
[Fact]
public void EnsureControllersThrowIfProvidedWithNull() {
foreach (var controller in ControllerTypes) {
var ctrs = GetConstructorsForType(controller);
if (null == ctrs || !ctrs.Any()) { //if the controller has no constructors, that's fine, we just skip over it
continue;
}
var ctr = ctrs.ElementAt(0);
var ctrParamsAsNull = ctr.GetParameters().Select(p => (object)null);
book ok = false;
try
{
ctr.Invoke(ctrParamsAsNull.ToArray());
}
catch(ArgumentNullException)
{
//you get exception you expected so continue
ok = true;
}
if(!ok)
{
// you didn't get exception so throw your own exception with message that contains controller type name
throw new Exception(String.Format("Ctor on type {0} did not throw ArgumentNullException",controller.Name);
}
}
}
这只是一个想法。你可以在你自己的静态断言方法中重构它......