fixture.CreateAnymous方法在使用Automoq创建控制器时,用错误(Autofuture)杀死测试跑步者进程

StackOverflow https://stackoverflow.com/questions/3514102

我正在尝试使用AutoFixture使用AutomoQcustomization来通过FIXPUTER.CREATEANYONMOUS方法在单元测试中创建ASP.NET MVC2控制器。我在Xunit testdriven.net,Xunit Test GUI和MSTest中都尝试过,所有这些都具有相同的结果:该过程运行测试的过程发生了巨大的故障。在Windows 7 x64上,如果很重要。

要复制,只需创建一个新的ASP.NET MVC2项目,请将引用添加到AutoFixture,Automoq和MOQ(根据AutomoQ源,3.1,根据Automoq源)添加,然后尝试以下(repro vs2010 MVC2项目链接):

[TestMethod]
public void Index()
{
 var fixture = new Fixture().Customize(new AutoMoqCustomization());
    // here's where the error in the test host occurs:
 HomeController controller = fixture.CreateAnonymous<HomeController>();
}

在mstest中,错误读取:

运行时遇到了致命的错误。该错误的地址为0x6465F370,在线程0x2684上。错误代码为0xC0000005。此错误可能是CLR中的错误,也可能是用户代码的不安全或不验证部分中的错误。此错误的常见来源包括Com-Interop或PinVoke的用户编制错误,这可能会破坏堆栈。

AFWITHMVC repro项目(来自SkyDrive)

有帮助吗?

解决方案

建议的解决方案

要从可能的解决方案开始,这应该阻止崩溃:

var fixture = new Fixture().Customize(new AutoMoqCustomization());
// This should fix the problem for all Controllers
fixture.Customize<ViewDataDictionary>(c =>
    c.Without(x => x.ModelMetadata));

HomeController controller = fixture.CreateAnonymous<HomeController>();

解释

现在进行解释:

此测试错误是由自动Fofture引起的 自动卷 尝试将值分配给 HomeController.ViewData.ModelMetaData. 。 ModelMetadata类具有此构造函数:

public ModelMetadata(
    ModelMetadataProvider provider,
    Type containerType,
    Func<object> modelAccessor,
    Type modelType,
    string propertyName)

罪魁祸首是 modelAccessor 范围。为了填充该属性自动固定(相当无知)可以反映出该类型,并找到了这个单个构造函数:

public Func(object @object, IntPtr method)

进一步挖掘,第一个INTPTR构造函数自动固定可以满足这一点:

public unsafe IntPtr(int value)

默认情况下, INT32实例是由确定性上升序列创建的, , 所以 value 在这种情况下,可能是1或2或类似的小整数。换句话说,我们现在有一个 非常无效 我们手上不安全的指针,这使过程崩溃。

现在,在正常情况下,我们应该能够通过注册 Func<object> 使用固定装置,一切都应该是花花公子:

fixture.Register<Func<object>>(() => () => new object());

但是,我尝试了您的repro,尽管该过程不再以相同的方式崩溃,但测试持续很长时间,最终以OutofMemoryException崩溃。

我不知道ASP.NET MVC有什么作用 Func<object>, ,但显然它使用它很重。

问题仍然是这是否是自动倒置中的错误?

我相信不是。虽然它绝对不是理想的,但自动框并没有与其他类型不同,这就是为什么我们看到这种行为的原因。

可以通过增加对 Func<TResult>, ,但是要保持一致,也应该支持 Func<T, TResult>, Func<T1, T2, TResult>, 等等。.NET 4中有AFAIR 很多 在这些委托类型(也是动作等)中,这将意味着增加对各种类型的支持。

但是,将所有其他类型都带入其构造函数的其他类型呢? Autofuture不可能全部了解它们,因此这似乎不像一个可行的方向。

但是,这是什么 可以 有一个 守卫首先试图创建INTPTR实例的守护. 。这很可能会在2.0 RTW之前添加。

感谢您报告。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top