2010-11-03 60 views
2

有没有办法使用字符串参数而不是表达式设置Moq模拟器?您可以使用受保护函数的受保护扩展来执行此操作,但如果公用则抛出异常。例如,这里是你如何可能设置与一个Moq的保护无效的功能:用字符串设置Moq的函数

myMock.Protected().Setup("MyProtectedFunction"); 

我希望能够做同样的事情与公共功能。如果我能做到这一点,我已经有了一些反射代码,可以返回我需要模拟的所有函数的名称,并且我希望能够在此基础上进行构建,以避免必须在庞大的工厂类上设置许多功能。

回答

3

有趣的问题,这几乎可以做到使用表达式。由于setup方法需要一个表达式,因此可以在运行时构建它。

需要在编译时发生的唯一一点是根据模拟方法的返回类型将表达式转换为适当的lambda类型。不幸的是,Moq没有提供Setup超负荷运行Expression,否则它可能会在运行时做到100%。

public abstract class Fruit 
{ 
} 

public class Apple :Fruit 
{ 
} 

public interface IFactory { 
    Fruit CreateFruit(string type); 
    void VoidMethod(int intParameter); 
} 

[TestClass] 
public class UnitTest1 { 
    [TestMethod] 
    public void TestMethod1() { 
     var factoryMock = new Mock<IFactory>(); 

     Expression factoryCall = Expression.Lambda(
      Expression.Call(Expression.Variable(typeof(IFactory), "f"), "CreateFruit", new Type[]{}, Expression.Constant("Apple")), 
      Expression.Parameter(typeof(IFactory), "f")); 

     //factoryMock.Setup(f=>f.CreateFruit("Apple")).Returns(new Apple()); 

     factoryMock.Setup((Expression<Func<IFactory, Fruit>>)factoryCall).Returns(new Apple()); 
     var ret = factoryMock.Object.CreateFruit("Apple"); 
     Assert.IsInstanceOfType(ret, typeof(Apple)); 
    } 
} 
+0

谢谢,有一些调整,这对我做了。 – 2010-11-04 17:53:07

+0

你有没有机会写出你如何解决整个问题?我正在尝试做类似的事情。 – 2011-06-23 21:12:35

+0

你好,你认为你可以提供这样的代码,但建立属性,而不是方法? 谢谢 – 2017-10-21 19:06:18