Using JPA 2.0 Criteria API and cast causes generated JPQL to fail in Hibernate

允我心安 提交于 2019-12-17 14:47:05

问题


I am a first time user of the new JPA 2.0 Criteria API and I 'm running into a problem when I need to cast a number field to String to compare it with a String parameter. Reason is that I want to search for partial numbers, so I use a 'like' on the CriteriaBuilder. Here's a code sample:

CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
        CriteriaQuery<ParcelDO> cq = cb.createQuery(ParcelDO.class);
        Root<ParcelDO> parcelDO = cq.from(ParcelDO.class);
        cq.select(parcelDO);

        String parcelNumberId = parcelSearchDetailDO.getParcelNumberId();
        if (parcelNumberId != null && !parcelNumberId.isEmpty()) {
            Predicate parcelNumberIdPredicate = cb.like(
                    parcelDO.<Long> get("parcelNumberId").as(String.class),
                    parcelNumberId + "%");

            if (cq.getRestriction() != null) {
                cq.where(cq.getRestriction(), parcelNumberIdPredicate);
            } else {
                cq.where(parcelNumberIdPredicate);
            }
        }

The important part is

Predicate parcelNumberIdPredicate = cb.like(
                    parcelDO.<Long> get("parcelNumberId").as(String.class),
                    parcelNumberId + "%");

where I use the Criteria API to convert the Path into a Expression needed for the like method on the CriteriaBuilder.

Now when I run and it executes this code, the underlying JPA 2.0 implementation Hibernate fails with the following exception:

Caused by: org.hibernate.hql.ast.QuerySyntaxException:
expecting CLOSE, found '(' near line 1, column 117 
[select generatedAlias0 from domain.ParcelDO as generatedAlias0 where
cast(generatedAlias0.parcelNumberId as varchar2(255 char)) like :param0]

Looks to me like Hibernate is generating a JPQL that is not correct.

I have no idea what is wrong, can you help?

I use the latest Hibernate version (3.6.0.CR2)

Thank you


回答1:


What it comes to JPA, Expression.as method is used to serve wrong purpose in question. Casting Expression<Number> to Expression<String> is not supposed to work via Expression.as. Of course it would be nice to have clear error message instead of incorrect JPQL.

As said in documentation, it performs typecast, which is different concept than conversion from type to other:

Perform a typecast upon the expression, returning a new expression object. This method does not cause type conversion: the runtime type is not changed. Warning: may result in a runtime failure.




回答2:


As axtavt stated in the comments in the question, it is a bug in Hibernate 3.6 http://opensource.atlassian.com/projects/hibernate/browse/HHH-5755



来源:https://stackoverflow.com/questions/4269389/using-jpa-2-0-criteria-api-and-cast-causes-generated-jpql-to-fail-in-hibernate

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!