How to configure an Equals call with a specific type that overlaps Equals in MoQ?

Working with the thin mocking-framework MoQ, I came across a somewhat unexpected aspect (and I don't like surprises). I am mocking the class that should be added to the collection after calling the method, for example:

public class SomeClass{

}

public class Container {
    private List<SomeClass> classes = new List<SomeClass>();

    public IEnumerable<SomeClass> Classes {
        get {
            return classes;
        }
    }

    public void addSomeClass(SomeClass instance) {
        classes.Add(instance);
    }
}

[Test]
public void ContainerContainsAddedClassAfterAdd() {
    var mockSomeClass = new Mock<SomeClass>();  
    mockSomeClass.Setup(c => c.Equals(mockSomeClass.Object)).Return(true);

    var Container = new Container();
    Container.addSomeClass(mockSomeClass.Object);

    Assert(Container.Classes.Contains(mockSomeClass.Object));
}

This works well, the layout is added to the collection, Containerand setting the method Equalsto mock ensures it IEnumerable.Contains()returns true. However, there is always some complication. The class that I am really mocking is not as simple as ours SomeClass. This is something like this:

public class SomeClassOverridingEquals{
    public virtual Equals(SomeClassOverridingEquals other) {
        return false;   
    }

    public override Equals(object obj) {
        var other = obj as SomeClassOverridingEquals;

        if (other != null) return Equals(other); // calls the override
        return false;
    }
}

[Test]
public void ContainerContainsAddedClassOverridingEqualsAfterAdd() {
    var mockSomeClass = new Mock<SomeClassOverridingEquals>();  
    mockSomeClass.Setup(c => c.Equals(mockSomeClass.Object)).Return(true);

    var Container = new Container();
    Container.addSomeClass(mockSomeClass.Object);

    Assert(Container.Classes.Contains(mockSomeClass.Object)); // fails
}

Equals , Setup , , ( Equals(object)). , .

, , .

.

- ?

+3
4

, Moq, Contains. Equals , Enumerable.Contains List<T>.Contains, Classes List<T>.

List<T>.Contains EqualityComparer<T>.Default.Equals, , Equals, System.Object, - : , mock, , System.Object .

EqualityComparer<T>.Default Reflector, , , IEquatable<T>, , ( ), -.

+6

. , Moq :

mockSomeClass.Setup(c => c.Equals((object)mockSomeClass.Object)).Return(true);
+1

SomeClass? ? , , , .

, mock. .

+1

ISomeClass . :

  • Mock<ISomeClass> unit test
  • It is best to combine the test on the actual unit test container separately from checking the actual implementation of the functionality of the SomeClass class.
0
source

Source: https://habr.com/ru/post/1718533/


All Articles