C# Mock.Verify()失败-此设置不匹配?

C# Mock.Verify()失败-此设置不匹配?,c#,moq,xunit,C#,Moq,Xunit,我有以下测试代码 var test = "Test"; var command = new MyCommand { V = test }; var mock = new Mock<IRepository>(); // IRepository has the method of Save() var p = new P(test); mock.Setup(x => x.Save(p)).Verifiable(); var sut = new C(mock.Object);

我有以下测试代码

var test = "Test";

var command = new MyCommand { V = test };

var mock = new Mock<IRepository>(); // IRepository has the method of Save()
var p = new P(test);
mock.Setup(x => x.Save(p)).Verifiable();

var sut = new C(mock.Object);
var result = await sut.M(command);

mock.Verify();
var test=“test”;
var命令=newmycommand{V=test};
var mock=new mock();//IRepository具有Save()的方法
var p=新的p(测试);
mock.Setup(x=>x.Save(p)).Verifiable();
var sut=新的C(mock.Object);
var结果=等待sut.M(命令);
mock.Verify();
考试应该通过。但是,它失败了,错误是

Message: Moq.MockException : Mock: This mock failed verification due to the following: IRepository x => x.Save(P): This setup was not matched. Stack Trace: Mock.Verify() 信息: Moq.Mock异常:Mock: 由于以下原因,此模拟验证失败: i存储x=>x.Save(P): 此设置不匹配。 堆栈跟踪: Mock.Verify()
sut.M()
将字符串X转换为值为
p(X)
的类型
p
,我认为您需要验证是否使用特定值而不仅仅是类型调用模拟中的Save方法

我已经尝试过下面这样的方法,并且相信它会起作用。我修改了你的例子

var test = "Test";

var command = new MyCommand { V = test };

var mock = new Mock<IRepository>(); 
IRepository has the method of Save()
var p = new P(test);
mock.Setup(x => x.Save(It.IsAny<P>());

var sut = new C(mock.Object);
var result = await sut.M(command);

mock.Verify(x => x.Save(It.Is<P>(v => v.Value.Equals(p.Value))), Times.AtLeastOnce);
var test=“test”;
var命令=newmycommand{V=test};
var mock=new mock();
IRepository具有Save()的方法
var p=新的p(测试);
mock.Setup(x=>x.Save(It.IsAny

()); var sut=新的C(mock.Object); var结果=等待sut.M(命令); mock.Verify(x=>x.Save(It.Is

(v=>v.Value.Equals(P.Value))),Times.atleastone);

这将测试特定属性的值是否相等

我通过以下测试对此进行了测试:

var test = "Test";

var mock = new Mock<ITestRepository>(); // ITestRepository has the method of Save()
var p = new P(test);
mock.Setup(x => x.Save(It.IsAny<P>()));

mock.Object.Save(new P(test));

mock.Verify(x => x.Save(It.Is<P>(v => v.Value.Equals(p.Value))), Times.AtLeastOnce);
var test=“test”;
var mock=new mock();//ITestRepository具有Save()方法
var p=新的p(测试);
mock.Setup(x=>x.Save(It.IsAny

()); mock.Object.Save(新的P(测试)); mock.Verify(x=>x.Save(It.Is

(v=>v.Value.Equals(P.Value))),Times.atleastone);


在我看来,您似乎想要验证是否使用特定的值而不仅仅是类型来调用模拟中的Save方法

我已经尝试过下面的方法,并且相信它应该有效。我已经修改了你的例子

var test = "Test";

var command = new MyCommand { V = test };

var mock = new Mock<IRepository>(); 
IRepository has the method of Save()
var p = new P(test);
mock.Setup(x => x.Save(It.IsAny<P>());

var sut = new C(mock.Object);
var result = await sut.M(command);

mock.Verify(x => x.Save(It.Is<P>(v => v.Value.Equals(p.Value))), Times.AtLeastOnce);
var test=“test”;
var命令=newmycommand{V=test};
var mock=new mock();
IRepository具有Save()的方法
var p=新的p(测试);
mock.Setup(x=>x.Save(It.IsAny

()); var sut=新的C(mock.Object); var结果=等待sut.M(命令); mock.Verify(x=>x.Save(It.Is

(v=>v.Value.Equals(P.Value))),Times.atleastone);

这将测试特定属性的值是否相等

我通过以下测试对此进行了测试:

var test = "Test";

var mock = new Mock<ITestRepository>(); // ITestRepository has the method of Save()
var p = new P(test);
mock.Setup(x => x.Save(It.IsAny<P>()));

mock.Object.Save(new P(test));

mock.Verify(x => x.Save(It.Is<P>(v => v.Value.Equals(p.Value))), Times.AtLeastOnce);
var test=“test”;
var mock=new mock();//ITestRepository具有Save()方法
var p=新的p(测试);
mock.Setup(x=>x.Save(It.IsAny

()); mock.Object.Save(新的P(测试)); mock.Verify(x=>x.Save(It.Is

(v=>v.Value.Equals(P.Value))),Times.atleastone);



Try
mock.Setup(x=>x.Save(It.IsAny

())

否则它期望通过完全相同的
P
,我怀疑
P
是否有值相等设置。我看不到
P
x.Save(P)之外的任何地方被使用
@juharr的观点就是我想说的。顺便说一句,Moq能验证一个方法没有被调用吗?是的,你可以做类似于
mock.verify(x=>x.Save(It.IsAny

(),Times.Never))的事情

。其他选项包括
一次
至少一次
,以及指定可以调用它的特定次数或次数范围的其他选项。您还可以使用
回调
获取参数,以便使用
测试
值,如
模拟设置(x=>x.Save),测试它是否通过了
P
(It.IsAny

()).Callback

(P=>Assert.Equal(P.whatever,test))

尝试
mock.Setup(x=>x.Save(It.IsAny

)否则它希望传递完全相同的
P
,我怀疑
P
是否有值相等设置。我看不到
P
以外的任何地方正在使用
x.Save(P)
@juharr的观点就是我想说的。顺便说一句,Moq能验证一个方法没有被调用吗?是的,你可以做类似于
mock.verify(x=>x.Save(It.IsAny

(),Times.Never))的事情

。其他选项包括
一次
至少一次
,以及指定可以调用它的特定次数或次数范围的其他选项。您还可以使用
回调
获取参数,以便使用
测试
值,如
模拟设置(x=>x.Save),测试它是否通过了
P
(It.IsAny

()).Callback

(P=>Assert.Equal(P.whatever,test))

顺便说一句,我发现即使我没有调用
.Verifiable()
?例如,
\u repositoryMock.Verify(x=>x.Add(It.IsAny()),Times.one)
没有它也能工作。是的@ca9163d9,这似乎是更好的验证方法。你可以通过阅读了解更多。我编辑了我的答案,使用了这种方法。在注释了
mock.Setup(x=>x.Save(it.IsAny

);

之后发现它可以工作。
更新的
验证(x=>…)
?我认为只要您正在测试的代码都不依赖于
Save
返回的内容或任何其他副作用,就没有必要进行设置。我认为您应该保留更新的
Verify
,如果您想测试方法是否以某个值调用。是的,我现在使用更新的版本。它的内涵和功能更加清晰
Times
的第二个参数很有用。谢谢。顺便说一句,我发现即使我没有调用
.Verifiable()
,它也可以工作。例如,
\u repositoryMock.Verify(x=>x.Add(it.IsAny()),Times.Once)
没有它也能工作。是的@ca9163d9,这似乎是更好的验证方法。你可以通过阅读了解更多。我编辑了我的答案,使用了这种方法。在注释了
mock.Setup(x=>x.Save(it.IsAny

);

之后发现它可以工作。
更新的
验证(x=>…)
?只要您正在测试的代码都不依赖于
Save
返回的内容或任何其他副作用,我认为设置是不必要的。我认为您应该保留