2012-08-22 66 views
1

我试图测试一个组成控件集合的方法。它调用两种方法:Presenter中的单元测试方法,MVP

  1. 复制原始集合。
  2. 排序新的集合。

理想情况下,id希望能够传入一个集合并进行测试,看看它是否正确排序。编号也想验证方法1)被调用了两次,见下文基于以下尝试:当我尝试创建MainPresenter的实例 Example using RhinoMock

下面的测试产生错误。一般jist的错误是“无法从Moq.Mock转换为”FrazerMann.CsvImporter.UserInterface.IMainForm。 +类似的一个IFileDialog。

[Test] 
    public void ComposeCollectionOfControls_CallSequence_4Calls() 
    { 
     var main = new Mock<IMainForm>(); 
     var dialog = new Mock<IFileDialog>(); 
     var temp = new Mock<IMainPresenter>(); 

     temp.Setup(s => s.PopulateLists<Control>(It.IsAny<TableLayoutPanel>(), It.IsAny<List<Control>>())); 

     var testObject = new MainPresenter(main.Object, dialog.Object); 
     testObject.ComposeCollectionOfControls(It.IsAny<object>(), It.IsAny<EventArgs>()); 
     temp.Verify(v => v.PopulateLists<Control>(It.IsAny<TableLayoutPanel>(), It.IsAny<List<Control>>()), Times.Once());   
    } 

我想测试ComposeCollectionOfControls确保PopulateList()被调用了两次。

public interface IMainPresenter 
{ 
    void PopulateLists<T>(TableLayoutPanel userInputs, List<T> container) where T : Control; 
    int SortList<T>(T control1, T control2) where T : Control; 
} 

public class MainPresenter:IMainPresenter 
{ 
    UserInputEntity inputs; 

    IFileDialog _dialog; 
    IMainForm _view; 

    public MainPresenter(IMainForm view, IFileDialog dialog) 
    { 
     _view = view; 
     _dialog = dialog; 
     view.ComposeCollectionOfControls += ComposeCollectionOfControls; 
     view.SelectCsvFilePath += SelectCsvFilePath; 
     view.SelectErrorLogFilePath += SelectErrorLogFilePath; 
     view.DataVerification += DataVerification; 
    } 

    public void ComposeCollectionOfControls(object sender, EventArgs e) 
    { 
     PopulateLists<TextBox>(_view.ColumnNameCtrls, _view.SortedColumnNameCtrls); 
     _view.SortedColumnNameCtrls.Sort(SortList<TextBox>); 
     PopulateLists<ComboBox>(_view.ColumnDataTypeCtrls, _view.SortedColumnDataTypeCtrls); 
     _view.SortedColumnDataTypeCtrls.Sort(SortList<ComboBox>); 
    } 
} 

可能有人请给我一些指点,如何这应该怎么办?

回答

3

您看到的错误是因为您正在传递模拟类本身(类型为Moq.Mock),而不是Moq为您创建的模拟对象。

相反的:

var testObject = new MainPresenter(main, dialog); 

你需要:

var testObject = new MainPresenter(main.Object, dialog.Object); 

顺便说一句,它通常被认为是不好的做法,明确地验证这样的方法调用在一个特定的制造数量的东西方法。这会导致测试和特定实现之间的紧密耦合,并因此导致脆弱的测试。

通过测试您调用某个方法的次数,在代码的最终结果仍然正确时重构某些代码后,您经常会发现测试失败。

测试所涉及对象的最终状态要好得多,并且让测试不知道该状态是如何达到的。

+0

脸掌!非常感谢David –

+0

非常感谢您对原始答案的编辑,我没有意识到这一点。出于好奇(这是我的事件处理程序调用一个单独的方法的原因,但你昨天提到这是错误的,所以即时通讯假设我犯了一个愚蠢的错误),我得到一个空对象错误,我假设是由于这条线“testObject .ComposeCollectionOfControls(It.IsAny (),It.IsAny ());“是否可以使用It.IsAny ()填写发件人/ e? –