在earlier question我询问了Autofixture CreateProxy method时,确定了potential bug。
我不认为这次失败的测试是由于这一点,而是我对Likeness.Without(...)。CreateProxy()语法如何工作的持续混淆。考虑以下失败测试,我通过创建对象的新实例使original test 变得更加复杂,将其创建视为SUT:
[Fact]
public void Equality_Behaves_As_Expected()
{
// arrange: intent -> use the fixture-created Band as Object Mother
var template = new Fixture().Create<Band>();
// act: intent -> instantiated Band *is* the SUT
var createdBand = new Band {Brass = template.Brass,
Strings = template.Brass};
// intent -> specify that .Brass should not be considered in comparison
var likeness = template.AsSource().OfLikeness<Band>().
Without(x => x.Brass).CreateProxy(); // Ignore .Brass property
// per [https://stackoverflow.com/a/15476108/533958] explicity assign
// properties to likeness
likeness.Strings = template.Strings;
likeness.Brass = "foo"; // should be ignored
// assert: intent -> check equality between created Band & template Band
// to include all members not excluded in likeness definition
likeness.Should().Be(createdBand); // Fails
likeness.ShouldBeEquivalentTo(createdBand); // Fails
Assert.True(likeness.Equals(createdBand)); // Fails
}
以下是乐队:
public class Band
{
public string Strings { get; set; }
public string Brass { get; set; }
}
我的earlier question并不够复杂,无法帮助我了解Source
Likeness
应该是什么。
源是否应该是SUT的输出,在这种情况下,它将与AutoFixture创建的模板实例进行比较?
或者源是否是AutoFixture创建的模板实例,在这种情况下,它会与SUT的输出进行比较?
编辑:更正了测试中的错误
我意识到我错误地将template.Brass
属性分配给 Brass
和新Strings
属性Band
个实例。更新的测试反映了var createdBand = new Band {Brass = template.Brass, Strings = template.Strings}
的更正,现在所有六个断言都已通过。
[Fact]
public void Equality_Behaves_As_Expected()
{
// arrange: intent -> use the fixture-created Band as Object Mother
var template = new Fixture().Create<Band>();
// act: intent -> instantiated Band *is* the SUT
var createdBand = new Band {Brass = template.Brass, Strings = template.Strings};
// likeness of created
var createdLikeness = createdBand.AsSource().OfLikeness<Band>().
Without(x => x.Brass).CreateProxy(); // .Brass should not be considered in comparison
// https://stackoverflow.com/a/15476108/533958 (explicity assign properties to likeness)
createdLikeness.Strings = createdBand.Strings;
createdLikeness.Brass = "foo"; // should be ignored
// likeness of template
var templateLikeness = template.AsSource().OfLikeness<Band>()
.Without(x => x.Brass)
.CreateProxy();
templateLikeness.Strings = template.Strings;
templateLikeness.Brass = "foo";
// assert: intent -> compare created Band to template Band
createdLikeness.Should().Be(template);
createdLikeness.ShouldBeEquivalentTo(template);
Assert.True(createdLikeness.Equals(template));
templateLikeness.Should().Be(createdBand);
templateLikeness.ShouldBeEquivalentTo(createdBand);
Assert.True(templateLikeness.Equals(createdBand));
}
答案 0 :(得分:3)
你的意思是:
likeness.Should().BeAssignableTo<Band>(); // Returns true.
在提供的示例中,从Likeness
生成的代理是从Band
派生的类型,使用语义比较算法覆盖Equals
。
使用反射:
createdBand.GetType().IsAssignableFrom(likeness.GetType()) // Returns true.
<强>更新强>:
createBand 和模板实例不受CreateProxy
方法的影响。他们为什么要这样做?
凭借相似CreateProxy
,您基本上可以创建一个允许您执行的Custom Equality Assertion:
Assert.True(likeness.Equals(createdBand)); // Passed.
没有它,最初的Equality Assertion将会失败:
Assert.True(template.Equals(createdBand)); // Failed.
但是,以下内容也将失败:
Assert.True(likeness.Equals(template));
失败是因为Strings
值是 createdBand 实例中的值。
此行为是预期的,您可以直接使用Likeness
验证它:
createdBand.AsSource().OfLikeness<Band>()
.Without(x => x.Brass).ShouldEqual(template);
输出:
The provided value `Band` did not match the expected value `Band`. The following members did not match:
- Strings.