使用Moq模拟具有内部构造函数的类型

Tom*_*son 27 c# unit-testing moq microsoft-sync-framework

我正在尝试从Microsoft Sync Framework模拟一个类.它只有一个内部构造函数.当我尝试以下内容时:

var fullEnumerationContextMock = new Mock<FullEnumerationContext>();
Run Code Online (Sandbox Code Playgroud)

我收到此错误:

System.NotSupportedException:Parent没有默认构造函数.必须显式定义默认构造函数.

这是堆栈跟踪:

System.Reflection.Emit.TypeBuilder.DefineDefaultConstructorNoLock(MethodAttributes attributes)System.Reflection.Emit.TypeBuilder.DefineDefaultConstructor(MethodAttributes attributes)System.Reflection.Emit.TypeBuilder.CreateTypeNoLock()System.Reflection.Emit.TypeBuilder.CreateType()Castle. DynamicProxy.Generators.Emitters.AbstractTypeEmitter.BuildType()Castle.DynamicProxy.Generators.ClassProxyGenerator.GenerateCode(Type [] interfaces,ProxyGenerationOptions options)Castle.DynamicProxy.DefaultProxyBuilder.CreateClassProxy(Type classToProxy,Type [] additionalInterfacesToProxy,ProxyGenerationOptions options)Castle. DynamicProxy.ProxyGenerator.CreateClassProxyType(Type classToProxy,Type [] additionalInterfacesToProxy,ProxyGenerationOptions options)Castle.DynamicProxy.ProxyGenerator.CreateClassProxy(Type classToProxy,Type [] additionalInterfacesToProxy,ProxyGenerationOptions options,Object [] constructorArguments,IInterceptor [] interceptors)Castle.DynamicProxy.ProxyGenerator.CreateClassProxy(Type classToProxy,Type [] additionalInterfacesToProxy,ProxyGenerationOptions options,IInterceptor [] interceptors)Castle.DynamicProxy .ProxyGenerator.CreateClassProxy(类型classToProxy,Type [] additionalInterfacesToProxy,IInterceptor []拦截器)Moq.MockDynamicProxy.ProxyGenerator.CreateClassProxy(类型classToProxy,Type [] additionalInterfacesToProxy,IInterceptor []拦截器)Moq.MockDynamicProxy.ProxyGenerator.CreateClassProxy(类型classToProxy,Type [] additionalInterfacesToProxy,IInterceptor []拦截器)Moq.Mock1.<InitializeInstance>b__0() Moq.PexProtector.Invoke(Action action) Moq.Mock1.InitializeInstance()

我该如何解决这个问题呢?

mar*_*ind 20

您不能模拟没有公共构造函数的类型,因为Moq将无法实例化该类型的对象.根据您要测试的内容,您有以下几种选择:

  1. 如果有工厂对象或其他获取FullEnumerationContext实例的方法,也许你可以使用它(抱歉,我不熟悉同步框架)
  2. 您可以使用私有反射来实例化FullEnumerationContext,但是您将无法在其上模拟方法.
  3. 您可以引入一个接口和/或包装器对象,它可以模拟被测试的代码可以调用.运行时实现将委托给真正的FullEnumerationContext,而您的测试时实现将执行您需要的任何操作.

  • @kzu由于您没有自己构建库,因此无法在第三方库上运行. (13认同)
  • 实际上,您可以使用内部构造函数实例化类的mock.您只需要将适当的InternalsVisibleTo属性应用于目标程序集,如https://code.google.com/p/moq/wiki/QuickStart中的"高级功能"中所述 (4认同)

Grz*_*nio 5

我并不是Moq的真正专家,但我认为您需要为构造函数指定参数。在Rhino Mocks中,您可以这样指定它们:

var fullEnumerationContextMock = new Mock<FullEnumerationContext>(arg1, arg2);
Run Code Online (Sandbox Code Playgroud)

Moq中可能与此类似。

  • 仅当您使用公共非默认构造函数对Moqing进行操作时,这才是正确的。对于内部构造函数(默认或其他),您很不走运。 (4认同)
  • 有人可以确认Moq是否可行?我正在使用Moq 3.1 (2认同)