Using the MOQ framework to compare objects or: why equals are (not always) equal

In our current project we try to use the MOQ framework in order to mock away database accesss in our business logic tests. I was testing some business logic where the executed method would compare different objects and aggregations of objects with each other in order to behave one way or the other. The method builds intersections of collections using the Except extension method and stores intermediate values in lists using the Equals method. Some first tests were successful where the database wasn't mocked. Introducing mocks made me bang my head on the table because of two reasons at least:
  • Getting used to the "over-Lambda'd" syntax of MOQ and trying to guess what was really meant on the MOQ QuickStart page. The documentation is rather sparse and a lot guess work and learning-by-pain seems to be the best way to get along. At least after some time you get along with the syntax and even start to like it.
  • Lists don't behave like they behaved before. WTF! Compare will always get you a false result, even though you are comparing the same objects. Except-statements will produce wrong lists as the wrong intersections are produced
What has happened there? After a sheer endless search, overloading the HashCode etc it simply comes down to that: MOQ always returns "0" as Hashcode for their objects and implemented the "Equals" method to always return false. Have a look at this:


var someMock = new Mock<Foo>();
var obj1 = someMock.Object;
var obj2 = someMock.Object;
bool bothEqual = obj1.Equals(obj2); // returns false!!
bool referenceEquals = ReferenceEquals(obj1, obj2); // returns true!

This is also the reason why any Collection manipulation extension mehtods will fail which rely on the Equals-method of the items inside the collection. There's a simple workaround to this: mock the Equals method and implement it correctly:

someMock.Setup(role => role.Equals(It.IsAny<object>())).Returns(
                    (object obj) => ReferenceEquals(obj, roleMock.Object));
 
 
This really made me scratch my head. Lucky we found it out, though.










Kommentare

  1. we have almost all country students as our subscribers for online course.We have 10+ years of experience we can serve various ascent people. oracle fusion Cloud HCM online training at erptree.com is worlds best online training center. we have excelent knowledge sharing Platform we have user friendly website where you
    will be provided with all the required details and Self-paced DEMO videos. we have our branches in pune, gurgaon, noida, india, usa, uk, uae, oracle fusion hcm training, fusion Procurement training, fusion hcm, scm training


    Oracle Fusion HCM Training

    AntwortenLöschen

Kommentar veröffentlichen

Beliebte Posts aus diesem Blog

Using a shared local network folder in a Windows environment as Git repository

Migrating an old .NET application including Crystal reports to the new world: A tale from the valley of sorrows