【问题标题】:JPA - How to query with a LIKE operator in combination with an AttributeConverterJPA - 如何使用 LIKE 运算符结合 AttributeConverter 进行查询
【发布时间】:2015-08-23 11:14:37
【问题描述】:

例如Customer 有一个PhoneNumber 类型的字段(值对象)。 在persistence.xml 中注册了一个PhoneNumberConverter,它实现了javax.persistence.AttributeConverter。此转换器将PhoneNumber 转换为字符串,反之亦然,因此JPA 提供程序能够将PhoneNumbers 存储到数据库中。

如何使用 Criteria API 在 PhoneNumber 上使用 LIKE 运算符查询 CustomerPhoneNumber 只能是有效的电话号码。 PhoneNumber 的值类似于 '+31%' 是不可能的。

【问题讨论】:

  • 你试过在 NamedQuery 中使用吗?
  • @Safwan Hijazi 在 Criteria API 中使用Predicates 可以方便地实现用于搜索“客户”的大型表单。当字段为空时,查询Customers时不应考虑。

标签: java jpa criteria-api


【解决方案1】:

简单的答案是使用NamedQuery,但您也可以使用CriteriaBuilder。请注意,您必须提供正确的类型和搜索词。

类似这样的:

CriteriaBuilder criteriaBuilder = entityManager.getCriteriaBuilder();
CriteriaQuery<Tuple> criteriaQuery = criteriaBuilder.createTupleQuery();
Root root = criteriaQuery.from(/*The class youre searching*/);
Predicate predicate = criteriaBuilder.like(root.<String>get(/*field name*/), /*search values*/);
criteriaQuery.where(predicate);
criteriaQuery.select(root);
TypedQuery query = entityManager.createQuery(criteriaQuery);
List<T> result = query.getResultList();

【讨论】:

  • 所有功劳归于 user489041。我添加了一个answer,为了完整起见,它继续使用客户的示例。
【解决方案2】:
public List<Customer> findCustomerByPhoneNumber(String phoneNumber) {
    EntityManager em = getEntityManager();
    CriteriaBuilder cb = em.getCriteriaBuilder();
    CriteriaQuery<Customer> cq = criteriaBuilder.createQuery();
    Root<Customer> customer = criteriaQuery.from(Customer.class);
    Predicate predicate = cb.like(customer.get(Customer_.phoneNumber).as(String.class), phoneNumber);
    cq.where(predicate);
    TypedQuery<Customer> query = entityManager.createQuery(criteriaQuery);

    return query.getResultList();
    }

其中phoneNumber 可能包含字符%
问题的解决方案是在PhoneNumberString:.as(String.class)的转换中。 PhoneNumber 必须覆盖 toString () 方法并返回电话号码。

Customer_ 提供了Customer 的元模型,可以由metamodel generator 生成。)

【讨论】:

  • 当心.as,它会在你的查询中生成cast(),可能会阻止它使用索引。
  • @chimmi 它仍然会这样做吗?列的 db 数据类型是文本?我的问题类似于 OP,除了 db 数据类型被特别选择为文本以允许有效的“喜欢”查询。在本机查询中工作正常,但现在我需要使用 Criteria API 进行基于表单的临时过滤。
  • 很有可能。但是你真的应该自己检查一下,只要启用日志试试,看看正在执行什么 sql。
猜你喜欢
  • 2011-03-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-06-05
  • 2021-05-27
  • 1970-01-01
  • 2010-12-26
  • 2021-05-11
相关资源
最近更新 更多