Moq如何正确模拟仅设置属性

时间:2010-05-17 22:20:44

标签: c# .net moq

使用Moq处理暴露的仅设置属性的接口的正确方法是什么?以前我已经添加了另一个访问者,但是这已经在我的域中渗透到整个过程中随机throw new NotImplementedException()语句。

我只想做一些简单的事情:

mock.VerifySet(view => view.SetOnlyValue, Times.Never());

但这会产生The property 'SetOnlyValue' has no getter

的编译错误

2 个答案:

答案 0 :(得分:18)

public class Xyz
{
    public virtual string AA { set{} }
}
public class VerifySyntax
{
    [Fact]
    public void ThisIsHow()
    {
        var xyz = new Mock<Xyz>();
        xyz.Object.AA = "bb";
        // Throws:
        xyz.VerifySet( s => s.AA = It.IsAny<string>(), Times.Never() );
    }
}
public class SetupSyntax
{
    [Fact]
    public void ThisIsHow()
    {
        var xyz = new Mock<Xyz>();
        xyz.SetupSet( s => s.AA = It.IsAny<string>() ).Throws( new InvalidOperationException(  ) );
        Assert.Throws<InvalidOperationException>( () => xyz.Object.AA = "bb" );
    }
}

答案 1 :(得分:2)

谢谢鲁本!

为了帮助某人使用VB.Net,这与VB.Net中的代码相同:

Public Interface Xyz
    WriteOnly Property AA As String
End Interface
Public Class VerifySyntax
    <Fact()>
    Public Sub ThisIsHow()
        Dim xyz = New Mock(Of Xyz)
        xyz.Object.AA = "bb"
        ' Throws:
        xyz.VerifySet(Sub(s) s.AA = It.IsAny(Of String)(), Times.Never())
    End Sub
End Class
Public Class SetupSyntax
    <Fact()>
    Public Sub ThisIsHow()
        Dim xyz = New Mock(Of Xyz)
        xyz.SetupSet(Sub(s) s.AA = It.IsAny(Of String)()).Throws(New InvalidOperationException())
        Assert.Throws(Of InvalidOperationException)(Sub() xyz.Object.AA = "bb")
    End Sub
End Class

重要的是,不能使用单行函数 lambda,因为这将被解释为返回值的表达式,而不是赋值语句你是谁。 这是因为VB.Net使用单个等号不仅用于赋值而且用于相等比较,所以试图做

        xyz.VerifySet(Function(s) s.AA = It.IsAny(Of String)(), Times.Never())

将被解释为s.AA值和It.IsAny(Of String)()的布尔比较,从而调用getter,这将再次导致编译错误。 相反,你想使用 Sub lambda(或者可能是多行函数lambda)。

但是,如果你在属性上有一个getter,那么一个Function lambda仍然可以工作。