C#中的Moq Application.Current.MainWindow

时间:2017-05-26 04:27:12

标签: c# wpf unit-testing moq viewmodel

我的视图模型中的代码如下所示。

private Generate()
{

// Some code here
var window = new CreateWindow
                {
                    Owner = Application.Current.MainWindow

                };
}

我想在单元测试中模拟MainWindow对象。我试过了

var app = new Application()
  mock.SetupGet(x => x._mainWindow)
              .Returns(It.IsAny<MainWindow>());

但MainWindow对象始终为null。

任何人都可以就此问题提供一些有用的指示。

2 个答案:

答案 0 :(得分:1)

您可以创建IMainWindowProvider接口和MainWindowProvider实现:

public interface IMainWindowProvider
{
    Window GetMainWindow();
}

public class MainWindowProvider : IMainWindowProvider
{
    public Window GetMainWindow() => Application.Current.MainWindow;
}

然后在您当前的Create方法代码中,您可以使用此服务的实例(该实例可以在您要测试的容器类的构造函数中设置,并且在应用程序中它将是MainWindowProvider类的实例,例如依赖注入):

var window = new CreateWindow
{
    Owner = mainWindowProvider.GetMainWindow()
};

在您的单元测试中,您可以模拟IMainWindowProvider而不是尝试模拟Application,并设置模拟以返回虚拟新窗口。

答案 1 :(得分:0)

您应该将new CreateWindow行包装到工厂模式。

创建一个新的WindowFactory类,它有一个方法和一个相应的接口IWindowFactory。

然后在Generate方法中调用注入的WindowFactory.Create()方法。

在你测试中注入一个模拟的IWindowFactory,它会返回一个虚假的窗口。

public interface IWindowFactory
{
  CreateWindow Create();
}

public class WindowFactory : IWindowFactory
{
  public CreateWindow Create() 
  {
    return new CreateWindow { Owner = Application.Current.MainWindow };
  }
}

在视图模型上添加属性

public IWindowFactory WindowFactory { get; set; }

在您的生成方法

var window = WindowFactory.Create();

然后在测试中,当您创建视图模型时,将WindowFactory设置为Mock