在Criteria API调用期间,有没有办法(本地)绕过或禁用AttributeConverter?

时间:2017-01-24 02:52:28

标签: java hibernate hibernate-criteria jpa-2.1

假设CreditcardNumb.class带有构造函数,用于检查信用卡号是否有效。

然后我创建一个CreditcardNumbConverter.class来将信用卡号码转换为数据库中的字符串:

public class CreditcardnumbConverter
      implements AttributeConverter<CreditcardNumb, String> {

    public String convertToDatabaseColumn(CreditcardNumb cn) {
        if (cn== null) return null;
        return cn.toString();
        }

    public CreditcardNumb convertToEntityAttribute(String cn) {
        if ((cn == null) || cn.trim().isEmpty()) return null;
        return new CreditcardNumb(cn);
        }
    }

这项工作正常,但现在我想使用 Hibernate的Criteria API (新的或旧的API)来搜索以“123”开头的信用卡号码:

CreditcardNumb cn = new CreditcardNumb("123");

createCriteria(Wallet.class)
      .add(Restrictions.ilike("creditcard", cn, MatchMode.START))
      .list();

但是,由于“123”不是有效的信用卡号,因此对象实例化失败。此外,这甚至不会编译,因为ilike方法只接受String s,而不接受CreditcardNumb s。

我的问题:

是否有任何方式(本地)绕过或禁用转换,以便我可以执行以下操作:

createCriteria(Wallet.class)
      .disable(CreditcardnumbConverter.class))
      .add(Restrictions.ilike("creditcard", "123", MatchMode.START))
      .list();

或者是否有其他方法可以使用Criteria API(不使用HQL)搜索以“123”开头的信用卡号码。

1 个答案:

答案 0 :(得分:2)

您可以将信用卡列映射到String类型的另一个属性:

@Entity
public class Wallet {

  private CreditcardNumb creditcard;

  @Column(name = ..., insertable = false, updatable = false)
  private String creditcardStr;

  ...
}

关键是要将此列映射为既不可插入也不可更新,以便其值不会持久化(否则Hibernate将不知道是否使用creditcardcreditcardStr值来更新底层数据库专栏)。

现在您的查询可能如下所示:

createCriteria(Wallet.class)
  .add(Restrictions.ilike("creditcardStr", "123", MatchMode.START))
  .list();