是否可以使用Moq(3.0+)分配一个out/ref参数?

我已经看过使用Callback(),但Action<>不支持ref参数,因为它是基于泛型的。我还希望在ref参数的输入上放置一个约束(It.Is),尽管我可以在回调中这样做。

我知道Rhino Mocks支持这个功能,但是我正在做的项目已经在使用Moq了。


当前回答

这是一个解决方案。

[Test]
public void TestForOutParameterInMoq()
{
  //Arrange
  _mockParameterManager= new Mock<IParameterManager>();

  Mock<IParameter > mockParameter= new Mock<IParameter >();
  //Parameter affectation should be useless but is not. It's really used by Moq 
  IParameter parameter= mockParameter.Object;

  //Mock method used in UpperParameterManager
  _mockParameterManager.Setup(x => x.OutMethod(out parameter));

  //Act with the real instance
  _UpperParameterManager.UpperOutMethod(out parameter);

  //Assert that method used on the out parameter of inner out method are really called
  mockParameter.Verify(x => x.FunctionCalledInOutMethodAfterInnerOutMethod(),Times.Once());

}

其他回答

这是一个解决方案。

[Test]
public void TestForOutParameterInMoq()
{
  //Arrange
  _mockParameterManager= new Mock<IParameterManager>();

  Mock<IParameter > mockParameter= new Mock<IParameter >();
  //Parameter affectation should be useless but is not. It's really used by Moq 
  IParameter parameter= mockParameter.Object;

  //Mock method used in UpperParameterManager
  _mockParameterManager.Setup(x => x.OutMethod(out parameter));

  //Act with the real instance
  _UpperParameterManager.UpperOutMethod(out parameter);

  //Assert that method used on the out parameter of inner out method are really called
  mockParameter.Verify(x => x.FunctionCalledInOutMethodAfterInnerOutMethod(),Times.Once());

}

就像这样:

被嘲笑的方法是

public bool GenerateClient(out Client client);

那么模拟部分将是:

Client client = new Client();
clintMockBll
.Setup(x => x.GenerateClient(out client))
.Returns((Client client1) =>
{
   client = new Client(){Name="Something"};
   return true;
});

在我简单地创建一个新的“Fake”类的实例来实现您试图Mock的任何接口之前,我在这里的许多建议中苦苦挣扎。然后,您可以简单地使用方法本身设置out参数的值。

似乎不可能开箱即用。看来有人想要解决问题

请看这个论坛帖子 http://code.google.com/p/moq/issues/detail?id=176

这个问题 用最小订货量验证参考参数的值

今天下午,我为此纠结了一个小时,但在任何地方都找不到答案。在我自己玩了一圈之后,我能够想出一个适合我的解决方案。

string firstOutParam = "first out parameter string";
string secondOutParam = 100;
mock.SetupAllProperties();
mock.Setup(m=>m.Method(out firstOutParam, out secondOutParam)).Returns(value);

这里的关键是mock.SetupAllProperties();这将为您清除所有属性。这可能并不适用于每个测试用例场景,但如果您所关心的只是获取YourMethod的返回值,那么这将很好地工作。