我正在做一些测试,以了解如何模拟使用对话框的方法。我有这个课程:
我的界面,这是MessageBox的包装。
public interface IDialogoDummy
{
ResultadoDialogo dummy(string paramMensaje, string paramCaption, System.Windows.MessageBoxButton paramBotones, MessageBoxResult paramBotonPorDefecto);
}
实现我的界面的类:
public class DialogoDummy : IDialogoDummy
{
//El método tiene que ser virtual para que moq pueda utilizarlo
public virtual ResultadoDialogo dummy(string paramMensaje, string paramCaption, System.Windows.MessageBoxButton paramBotones, MessageBoxResult paramBotonPorDefecto)
{
MessageBoxResult resultado = System.Windows.MessageBox
.Show(paramMensaje,
paramCaption,
paramBotones,
MessageBoxImage.None,
paramBotonPorDefecto);
if(resultado == MessageBoxResult.Cancel)
{
return ResultadoDialogo.Cancel;
}
else if(resultado == MessageBoxResult.No)
{
return ResultadoDialogo.No;
}
else if(resultado == MessageBoxResult.None)
{
return ResultadoDialogo.None;
}
else if(resultado == MessageBoxResult.OK)
{
return ResultadoDialogo.OK;
}
else if(resultado == MessageBoxResult.Yes)
{
return ResultadoDialogo.Yes;
}
else
{
return ResultadoDialogo.Unknown;
}
}
}
使用我的方法的类:
public class DialogoDummyMethods
{
//El método tiene que ser virtual para que moq pueda utilizarlo
public int getInt()
{
IDialogoDummy miGestor = new DialogoDummy();
ResultadoDialogo resultado = miGestor.dummy("OK es 0 y cancel es 1", "Test", MessageBoxButton.OKCancel, MessageBoxResult.Cancel);
int intResultado;
if (resultado == ResultadoDialogo.OK)
{
intResultado = 0;
}
else
{
intResultado = 1;
}
return intResultado;
}
}
这是我的测试:
[TestMethod]
public void DialogoTest01()
{
//La clase que se va a probar, que en este caso tiene también el método que se tiene que hacer mock, de modo.
Mock<IDialogoDummy> miDialogoDummyMock = new Mock<IDialogoDummy>();
//Se indica que cuando se llame al método dummy, con cualquier cadena tanto de mensaje como de caption, y con botones OKCancel y valor por
//defecto Canceal, devuelva 0.
miDialogoDummyMock.Setup(x => x.dummy(It.IsAny<string>(), It.IsAny<string>(), System.Windows.MessageBoxButton.OKCancel, System.Windows.MessageBoxResult.Cancel))
.Returns(GTS.CMMS.Client.Dialogos.ResultadoDialogo.OK);
DialogoDummyMethods misMetodos = new DialogoDummyMethods();
int intResultado = misMetodos.getInt();
Assert.AreEqual(0, intResultado, "Debería ser 0");
}
问题是模拟对象与我想要测试的方法中创建的对象不同,因此当执行测试方法时,会显示messageBox,我必须选择一个选项。
如何在不需要在对话框中选择选项的情况下测试我的getInt方法?
非常感谢。
答案 0 :(得分:1)
您的SUT(您正在测试的课程)应仅依赖于抽象。不要在类中实例化依赖关系 - 这会引入对具体类的依赖,这是您无法模拟的。通过构造函数/属性/参数依赖注入注入依赖项。这将允许您提供模拟的依赖项实现。
所以,一起:
1)取决于抽象
public class DialogoDummyMethods
{
private IDialogoDummy miGestor;
public int getInt()
{
// DialogoDummyMethods knows nothing about IDialogoDummy implementation
var resultado = miGestor.dummy(
"OK es 0 y cancel es 1", "Test",
MessageBoxButton.OKCancel, MessageBoxResult.Cancel);
return resultado == ResultadoDialogo.OK ? 0 : 1;
}
}
2)通过构造函数注入抽象。注意 - 如果只有一个方法需要IDialogoDummy,那么你可以将它作为方法参数注入(在这种情况下你不需要IDialogDummy作为类字段)
public DialogoDummyMethods(IDialogoDummy miGestor)
{
this.miGestor = miGestor;
}
3)对单元测试进行模拟依赖,并将模拟依赖注入正在测试的类
var miDialogoDummyMock = new Mock<IDialogoDummy>();
// setup mock here
var misMetodos = new DialogoDummyMethods(miDialogoDummyMock.Object);
int intResultado = misMetodos.getInt();
Assert.AreEqual(0, intResultado, "Debería ser 0");