【问题标题】:QueryDSL + PathBuilder + cast to stringQueryDSL + PathBuilder + 转换为字符串
【发布时间】:2015-03-30 13:28:13
【问题描述】:

我正在使用动态过滤器过滤 PrimeFaces 数据表。我使用 Spring org.springframework.data.jpa.domain.Specification 进行了这项工作。现在我想知道如何使用 QueryDSL 来做同样的事情。

使用规范,我可以使用javax.persistence.criteria.Root 获得javax.persistence.criteria.Join,使用javax.persistence.criteria.Expression.as(Class<String> type) 将其转换为String,最后使用javax.persistence.criteria.CriteriaBuilder.like(Expression<String> x, String pattern, char escapeChar)

如何在 QueryDSL 中做同样的事情?我可以使用 new PathBuilder<T>(clazz, "entity") 获取 PathBuilder(你真的必须在这里使用变量吗?我希望我的类是通用的......)但是 com.mysema.query.types.path.PathBuilder.get(String property) 返回新的 PathBuilder 而不是表达式。

如果我尝试使用com.mysema.query.types.path.PathBuilder.getString(String property),我会得到java.lang.IllegalArgumentException: Parameter value [1] did not match expected type [java.lang.Integer]

似乎我缺少的部分是演员表。 我很确定有人已经在处理同样的事情了。

谢谢。

编辑:IllegalArgumentException 的堆栈跟踪

尝试使用 com.mysema.query.types.path.PathBuilder.getString(String property) 在整数列中搜索文本“1” - 这就是我需要进行强制转换的地方:

Caused by: java.lang.IllegalArgumentException: Parameter value [1] did not match expected type [java.lang.Integer] at org.hibernate.ejb.AbstractQueryImpl.validateParameterBinding(AbstractQueryImpl.java:375) at org.hibernate.ejb.AbstractQueryImpl.registerParameterBinding(AbstractQueryImpl.java:348) at org.hibernate.ejb.QueryImpl.setParameter(QueryImpl.java:375) at org.hibernate.ejb.QueryImpl.setParameter(QueryImpl.java:442) at org.hibernate.ejb.QueryImpl.setParameter(QueryImpl.java:72) at com.mysema.query.jpa.impl.JPAUtil.setConstants(JPAUtil.java:44) at com.mysema.query.jpa.impl.AbstractJPAQuery.createQuery(AbstractJPAQuery.java:130) at com.mysema.query.jpa.impl.AbstractJPAQuery.createQuery(AbstractJPAQuery.java:97) at com.mysema.query.jpa.impl.AbstractJPAQuery.list(AbstractJPAQuery.java:240) at org.springframework.data.jpa.repository.support.QueryDslJpaRepository.findAll(QueryDslJpaRepository.java:102) ...

【问题讨论】:

  • 你能提供完整的堆栈跟踪吗?
  • @user1622058 你最后解决了吗?
  • 最后我创建了一个 DTO 并使用 stringValue() 手动组装谓词...不是最好的方法,但还没有找到更好的方法...
  • @user1622058:我有同样的问题。你能发布你的解决方案吗?

标签: dynamic casting path querydsl


【解决方案1】:

要获得有效条件,您需要考虑属性的类型,例如

pathBuilder.getNumber(Integer.class, property).stringValue().like(likePattern)

【讨论】:

  • 对不起,正在度假...我知道这一点,但有什么办法可以动态地做到这一点?我的输入类似于“属性”,但我不知道数据库中的这个属性是什么类型,所以我不知道是否调用 getNumbergetBooleangetDate 任何其他吸气剂......
【解决方案2】:

在遇到这个老问题之前,我一直在研究类似的主题。希望我的回答对大家有所帮助。

我认为可能的解决方案(完全)位于 QueryDSL 之外。您可以使用常见的 Java 反射来获取字段类型,例如

Class type = clazz.getDeclaredField(criteria.getKey()).getType();
// don't forget to catch exception if field doesn't exist ..
switch(type.getSimpleName()) {
    case "String": 
         StringExpression exp =  entityPath.getString(...);
}

这样你就可以有一个合理的动态实现。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-10
    • 2019-01-05
    • 1970-01-01
    • 2014-10-19
    • 2015-01-18
    • 2011-09-22
    相关资源
    最近更新 更多