Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allows BeEquivalentTo to handle a non-generic collection as the SUT #975

Merged
merged 1 commit into from Nov 19, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
@@ -1,4 +1,5 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
Expand Down Expand Up @@ -61,7 +62,7 @@ public bool CanHandle(IEquivalencyValidationContext context, IEquivalencyAsserti
MethodCallExpression executeExpression = Expression.Call(
Expression.Constant(validator),
ExpressionExtensions.GetMethodName(() => validator.Execute<object>(null, null)),
new[] { typeOfEnumeration },
new[] {typeOfEnumeration},
subjectAsArray,
expectationAsArray);

Expand All @@ -82,18 +83,23 @@ private static bool AssertSubjectIsCollection(object expectation, object subject
{
bool conditionMet = AssertionScope.Current
.ForCondition(!(subject is null))
.FailWith("Expected {context:Subject} not to be {0}.", new object[] { null });
.FailWith("Expected {context:subject} not to be {0}.", new object[] {null});

if (conditionMet)
{
conditionMet = AssertionScope.Current
.ForCondition(IsGenericCollection(subject.GetType()))
.FailWith("Expected {context:Subject} to be {0}, but found {1}.", expectation, subject);
.ForCondition(IsCollection(subject.GetType()))
.FailWith("Expected {context:subject} to be a collection, but it was a {0}", subject.GetType());
}

return conditionMet;
}

private static bool IsCollection(Type type)
{
return !typeof(string).IsAssignableFrom(type) && typeof(IEnumerable).IsAssignableFrom(type);
}

private static bool IsGenericCollection(Type type)
{
var enumerableInterfaces = GetIEnumerableInterfaces(type);
Expand All @@ -120,7 +126,7 @@ private static MethodCallExpression ToArray(object value, Type typeOfEnumeration
return Expression.Call(
typeof(Enumerable),
"ToArray",
new[] { typeOfEnumeration },
new[] {typeOfEnumeration},
Expression.Constant(value, typeof(IEnumerable<>).MakeGenericType(typeOfEnumeration)));
}
}
Expand Down
44 changes: 19 additions & 25 deletions Tests/Shared.Specs/CollectionEquivalencySpecs.cs
Expand Up @@ -649,6 +649,24 @@ public void
.WithMessage("*Customers[0].Name*John*Jane*");
}


[Fact]
public void When_the_subject_is_a_non_generic_collection_it_should_still_work()
{
//-----------------------------------------------------------------------------------------------------------
// Arrange
//-----------------------------------------------------------------------------------------------------------
object item = new object();
object[] array = new[] { item };
IList readOnlyList = ArrayList.ReadOnly(array);


//-----------------------------------------------------------------------------------------------------------
// Act / Assert
//-----------------------------------------------------------------------------------------------------------
readOnlyList.Should().BeEquivalentTo(array);
}

[Fact]
public void
When_a_collection_property_was_expected_but_the_property_is_not_a_collection_it_should_throw
Expand Down Expand Up @@ -685,7 +703,7 @@ public void
//-----------------------------------------------------------------------------------------------------------
act.Should().Throw<XunitException>()
.WithMessage(
"*member Customers to be {*Customer*{*Age*38*, but*Jane, John*");
"Expected*Customers*collection*String*");
}

[Fact]
Expand Down Expand Up @@ -1598,30 +1616,6 @@ public void When_subject_is_null_and_expectation_is_enumerable_it_should_throw()
"Expected subject not to be <null>*");
}

[Fact]
public void When_the_expectation_is_not_a_multi_dimensional_array_it_should_throw()
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❓ Why is this test no longer valid?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because since v5, the expectation drives the type of comparison. Since it's a string, it'll never trigger the MultiDimensionalArrayEquivalencyStep

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense.
Couldn't see how that test should be affected by the other changes in this PR.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Don't even understand how this entire bug only surfaced now.

{
//-----------------------------------------------------------------------------------------------------------
// Arrange
//-----------------------------------------------------------------------------------------------------------
var actual = new[,]
{
{ 1, 2, 3 },
{ 4, 5, 6 }
};

//-----------------------------------------------------------------------------------------------------------
// Act
//-----------------------------------------------------------------------------------------------------------
Action act = () => actual.Should().BeEquivalentTo("not-a-multi-dimensional-array");

//-----------------------------------------------------------------------------------------------------------
// Assert
//-----------------------------------------------------------------------------------------------------------
act.Should().Throw<XunitException>()
.WithMessage("Expected*not-a-multi-dimensional-array*but found {1, 2, 3, 4, 5, 6}*");
}

[Fact]
public void When_the_expectation_is_null_it_should_throw()
{
Expand Down