C# 这可以用最小起订量来嘲弄吗?
我正在模拟一些外部依赖项,并且在一个第三方类中遇到了问题,这个第三方类的构造函数中包含了另一个第三方类的实例。希望SO社区能给我一些指导 我想创建一个C# 这可以用最小起订量来嘲弄吗?,c#,.net,unit-testing,mocking,moq,C#,.net,Unit Testing,Mocking,Moq,我正在模拟一些外部依赖项,并且在一个第三方类中遇到了问题,这个第三方类的构造函数中包含了另一个第三方类的实例。希望SO社区能给我一些指导 我想创建一个SomeRelatedLibraryClass的模拟实例,它接受它的构造函数SomeLibraryClass的模拟实例。我怎样才能用这种方式模拟某个相关的库类 回购代码… 下面是我在测试控制台应用程序中使用的一个主要方法 public static void Main() { try { SomeLibraryCla
SomeRelatedLibraryClass
的模拟实例,它接受它的构造函数SomeLibraryClass
的模拟实例。我怎样才能用这种方式模拟某个相关的库类
回购代码…
下面是我在测试控制台应用程序中使用的一个主要方法
public static void Main()
{
try
{
SomeLibraryClass slc = new SomeLibraryClass("direct to 3rd party");
slc.WriteMessage("3rd party message");
Console.WriteLine();
MyClass mc = new MyClass("through myclass");
mc.WriteMessage("myclass message");
Console.WriteLine();
Mock<MyClass> mockMc = new Mock<MyClass>("mock myclass");
mockMc.Setup(i => i.WriteMessage(It.IsAny<string>()))
.Callback((string message) => Console.WriteLine(string.Concat("Mock SomeLibraryClass WriteMessage: ", message)));
mockMc.Object.WriteMessage("mock message");
Console.WriteLine();
}
catch (Exception e)
{
string error = string.Format("---\nThe following error occurred while executing the snippet:\n{0}\n---", e.ToString());
Console.WriteLine(error);
}
finally
{
Console.Write("Press any key to continue...");
Console.ReadKey();
}
}
以下是我正在使用的两个第三方类的示例(您不能编辑这些类):
好了,如果你试图模拟的类不是虚拟的或者不是接口,你就不能用Moq来模拟它。如果您的第三方库没有实现它们的类,我认为您运气不好。我建议使用该模式。与其直接依赖于某个RelatedLibraryClass,不如创建一个接口异构RelatedLibraryClassGateway。公开所有需要使用异构相关LibraryClassGateway上具有相同签名的方法调用的RelatedLibraryClass方法
public interface ISomeRelatedLibraryClassGateway {
void WriteMessage(string message);
}
然后创建一个将所有调用路由到第三方类的实现:
public class SomeRelatedLibraryClassGateway : ISomeRelatedLibraryClassGateway {
private readonly SomeRelatedLibraryClass srlc;
public SomeRelatedLibraryClassGateway(SomeRelatedLibraryClass srlc) {
this.srlc = srlc;
}
void ISomeRelatedLibraryClassGateway.WriteMessage(string message) {
srlc.WriteMessage(message);
}
}
现在,应用程序中依赖于某个RelatedLibraryClass的类可以改为依赖于异构RelatedLibraryClassGateway,这个接口很容易模拟。类SomeRelatedLibraryClassGateway实际上不需要单元测试;它所做的就是把电话传过去。它确实需要在功能测试中进行测试,但是您可以在没有模拟的情况下进行功能测试
希望这有帮助。实际上,问题是我需要模拟SomeRelatedLibraryClass,它作为SomeLibraryClass类型的参数。我不清楚网关模式如何让我更容易地模拟那个类。在集成外部依赖项时,我通常使用网关模式,但在本例中,我省略了接口定义和实现,因为我认为它与问题无关。重点是避免模拟某些RelatedLibraryClass。使用网关模式可以避免模拟某些RelatedLibraryClass,因为(大部分)代码并不直接依赖于它。这是一个重构代码以便更容易测试的示例。
public interface ISomeRelatedLibraryClassGateway {
void WriteMessage(string message);
}
public class SomeRelatedLibraryClassGateway : ISomeRelatedLibraryClassGateway {
private readonly SomeRelatedLibraryClass srlc;
public SomeRelatedLibraryClassGateway(SomeRelatedLibraryClass srlc) {
this.srlc = srlc;
}
void ISomeRelatedLibraryClassGateway.WriteMessage(string message) {
srlc.WriteMessage(message);
}
}