使用Mock将属性Row设置为Mocked Microsoft.Office.Interop.Excel.Range



我想模拟Microsoft.Office.Interop.Excel.Range及其后,以便能够获取属性Row(第一个Row of Range的索引)。Moq v 4.1.1309.1617/nunit.framework v 2.6.3.13283在我的单元测试中,我尝试设置mock的行为如下:

var moqRowSelected = new Mock<Range>();
const int row = 1;
moqRowSelected.SetupGet(x => x.Row).Returns(row);
moqSheetBase.SetupProperty(x => x.RowSelected, moqRowSelected.Object);

在正在进行单元测试的代码中,我使用的范围如下:

var iRow = PlanningSheet.RowSelected.Row;
Range row = sheet.Rows[iRow];

当测试运行时,它会产生以下异常:

错误:缺少方法"instance int32"[My.Example.Elementation.MyClass]来自类的Microsoft.Office.Interop.Excel.Range::get_Row()'"Castle.Proxies.RangeProxy".

我如何才能成功地实现这种嘲讽?有人能帮我吗,谢谢。

我认为您已经正确地模拟了PlanningSheet.RowSelected引用的对象,因此iRow应该是正确的。但是,您没有正确模拟工作表返回的范围。行

让我们按照重写测试中的代码

 var iRow = PlanningSheet.RowSelected.Row;
 Range rows = sheet.Rows;
 Range row = rows.get_Range(iRow);

我敢打赌,变量中包含的mock不包含get_Range()的实现,该实现是索引属性后面的方法。

就我个人而言,我避免索引属性是因为嘲笑问题参见模拟索引属性

因此,以下代码似乎可以在您的案例中启用mocking。请注意,我没有访问PlanningSheet类型的权限,因此我将属性RowSelected引用的对象作为方法CodeUnderTest的参数进行传递

    private Range CodeUnderTest(Range rowSelected, Worksheet worksheet)
    {
        int index = rowSelected.Row;
        var range = worksheet.Rows.get_Range(index);
        return (Range) range;
    }
    [TestMethod]
    public void MySampleTest()
    {
        var moqRowSelected = new Mock<Range>();
        const int row = 1;
        moqRowSelected.SetupGet(x => x.Row).Returns(row);
        var moqRows = new Mock<Range>();
        moqRows.Setup(x => x.get_Range(It.Is<object>( (i) => (int) i==row),It.IsAny<object>())).Returns(moqRowSelected.Object);
        var mockWorksheet = new Mock<Worksheet>();
        mockWorksheet.SetupGet(w => w.Rows).Returns(moqRows.Object);
        var result = CodeUnderTest(moqRowSelected.Object, mockWorksheet.Object);
        Assert.IsNotNull(result);
    }

最后,您将看到必须在mock中为方法get_Range提供所有参数。这是因为如果不这样做,它将无法编译。错误很明显表达式树不能包含使用可选参数的调用

相关内容

最新更新