|
|
|
|
|
|
Hibernate recognizes a number of special "collection properties" when querying collections. This includes things like the size of the collection, the maxindex, the minindex, etc. The historical way to reference these was to use a "pseudo property" in the query. E.g., in HQL you'd have said {{select ... from Room r join r.walls w where w.size > 1}}. However that causes an ambiguity and "hides" a possible "real" attribute {{Wall#size}}. The preferred way to refer to these is using a "collection function" any way ({{... size(w) > 1}}) because there is no ambiguity.
In cases where the element actually defines an attribute that is also one of these "pseudo collection properties", prefer the interpretation using the Entity attribute.
---- h4. Original description
+In short+: * Two JPA-entites A and B are mapped via @OneToMany. * B contains an enum field named 'size'. * When querying (JPA-Criteria-API) on 'A join B' using where on the field 'size', java.lang.IllegalArgumentException (Parameter value [...] did not match expected type [java.lang.Integer]) is thrown. * Renaming the field to anything other than 'size' fixes the issue.
+More detailed:+
{code:java} @Entity public class A { @OneToMany(cascade={CascadeType.ALL}) private List<B> bs; ... } {code}
{code:java} @Entity public class B { @Enumerated(EnumType.STRING) private AnyEnumType size; ... } {code}
{code:java} //Method fails with exception public List<A> findBySize(AnyEnumType size) { CriteriaBuilder criteriaBuilder = entityManager.getCriteriaBuilder(); CriteriaQuery<A> query = criteriaBuilder.createQuery(A.class); Root<A> root = query.from(A.class); Path<AnyEnumType> path = root.<A,B>join("bs").<AnyEnumType>get("size"); query.where(criteriaBuilder.equal(path, size)); //Throws here return entityManager.createQuery(query).getResultList(); } {code}
The following exception is thrown: {code:java} java.lang.IllegalArgumentException: Parameter value [LARGE] did not match expected type [java.lang.Integer (n/a)] at org.hibernate.jpa.spi.BaseQueryImpl.validateBinding(BaseQueryImpl.java:858) at org.hibernate.jpa.internal.QueryImpl.access$000(QueryImpl.java:62) at org.hibernate.jpa.internal.QueryImpl$ParameterRegistrationImpl.bindValue(QueryImpl.java:235) at org.hibernate.jpa.spi.BaseQueryImpl.setParameter(BaseQueryImpl.java:603) at org.hibernate.jpa.spi.AbstractQueryImpl.setParameter(AbstractQueryImpl.java:163) at org.hibernate.jpa.spi.AbstractQueryImpl.setParameter(AbstractQueryImpl.java:32) at org.hibernate.jpa.criteria.compile.CriteriaCompiler$1$1.bind(CriteriaCompiler.java:109) at org.hibernate.jpa.criteria.CriteriaQueryImpl$1.buildCompiledQuery(CriteriaQueryImpl.java:369) at org.hibernate.jpa.criteria.compile.CriteriaCompiler.compile(CriteriaCompiler.java:130) at org.hibernate.jpa.spi.AbstractEntityManagerImpl.createQuery(AbstractEntityManagerImpl.java:699) ... {code}
Attached you'll find one testcase to reproduce the issue.
|
|
|
|
|
|