Hi,
after upgrade from 5.1.15 to 5.3.6 I observed one change related to getSingleResult() method's behaviour on some databases (some other DBs seem to be working OK, maybe it depends on dialect/driver).
In 5.1.15, when there were just duplicates in the result coming from DB, e.g. I was doing a projection on one attribute of type String, so the result from DB was for example
name ----------- John John
getSingleResult() method call was working in the way that it filtered out duplicates (using HashSet) and I got a single unique result, so no need for NonUniqueResultException, since result is unique (although duplicated) here.
Here is the code responsible for filtering out of duplicates: https://github.com/hibernate/hibernate-orm/blob/696abff61ca0218f42449e2bae4e03719528b4ae/hibernate-entitymanager/src/main/java/org/hibernate/jpa/internal/QueryImpl.java#L536-L546
However, with Hibernate 5.3.6 I am getting NonUniqueResultException in these scenarios. Although there is a filtering, it is done a little bit differently now. There is a uniqueElement method used in AbstractProducedQuery#getSingleResult() method:
https://github.com/hibernate/hibernate-orm/blob/5.3/hibernate-core/src/main/java/org/hibernate/query/internal/AbstractProducedQuery.java#L1569-L1580
Note this part:
{code:java} for ( int i = 1; i < size; i++ ) { if ( list.get( i ) != first ) { throw new NonUniqueResultException( list.size() ); } } {code}
I believe the cause of this different behaviour is that equals() method is not used there, rather "==" operator is, which means we compare here object's addresses, so in 99% of cases the condition will be true even though the content of the List would be just duplicates. If there was equals() my example would work as before on Hibernate 5.1.15, which was using HashSet, which in fact internally uses equals() as well.
Do you think this can be changed? I can help with a PR if you want, it looks like an easy change.
Thank you.
Marian
|
|