hibernate/hibernate-tools — pull request #45 by karlvr (2014-05-08 11:44:59+00:00)
Title: HBX-1226 Generated equals(Object) implementation doesn't support lazy proxies

Please accept my apologies for the previous, butchered and a bit lazy pull request.

This is entirely independent of #43, don't contain mistaken additions, and includes a test case demonstrating the fault before and the fix.

The fault is in the equals(Object other) implementation when other is a proxy, because the method uses instanceof to check if other is an instanceof the class. My solution uses Hibernate.getClass(Object), which is proxy aware, and compares that with == to getClass(). This is semantically different, obviously, as previously we had instanceof. We could replicate the old behaviour with getClass().isAssignableFrom(Hibernate.getClass(other)), but I think that comparing that we are the identical class is more correct.

This does also require that the proxy interface implements all of the methods that we include in the equals computation. I don't think this is a bad requirement, but it is an extra requirement. We could bypass this requirement by busting open the proxy, but I think that's a little dirty.

I think this is a really important change as it introduces some very weird and subtle behaviour that results in unexpected failures. Specifically, note the testTwoIdenticalProxiesAreNotEqual() method where we demonstrate that for two proxies of the same object: p1 == p2 && !p1.equals(p2), which is pretty darn weird!