我有一个如下的实体:
@Entity
public class Country implements Serializable {
private static final long serialVersionUID = 1L;
@Id
private Long id;
@Type(type="secureString") //This is my custom user type and it is working fine in the sense I am able to insert, select and update records using it.
private SecureString nationality;
// getters and setters
}
SecureString类如下:
public class SecureString implements Serializable {
private static final long serialVersionUID = 1L;
private String actualValue;
private String formattedValue;
//getters and setters
}
The column name in db for this attibute is named "nationality"
只有一列与国籍相对应。我正在使用Hibernate Custom UserType
。之前此属性的类型为String
,而不是SecureString
。
我收到例外java.lang.IllegalArgumentException: org.hibernate.QueryException: could not resolve property: actualValue of: mypackge.Country.
形成的HQL是:
select s FROM mypackage.Country s
WHERE LOWER(s.nationality.actualValue) LIKE LOWER(:nationality_actualValue);
根据日志,我们可以看到Hibernate正在尝试在actualValue
类中找到名为Country
的属性,同时将HQl转换为SQl。我该如何解决这个问题?
注意:我还希望我可以在同一个Entity类中使用SecureString类型的多个属性。
日志:
at org.hibernate.QueryException.generateQueryException(QueryException.java:120) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.QueryException.wrapWithQueryString(QueryException.java:103) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:217) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:141) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:115) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:77) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:153) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.internal.AbstractSharedSessionContract.getQueryPlan(AbstractSharedSessionContract.java:545) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.internal.AbstractSharedSessionContract.createQuery(AbstractSharedSessionContract.java:654) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
... 142 common frames omitted
Caused by: org.hibernate.QueryException: could not resolve property: actualValue of: mypackage.Country
at org.hibernate.persister.entity.AbstractPropertyMapping.propertyException(AbstractPropertyMapping.java:62) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.persister.entity.AbstractPropertyMapping.toType(AbstractPropertyMapping.java:56) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.persister.entity.AbstractEntityPersister.toType(AbstractEntityPersister.java:1859) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.tree.FromElementType.getPropertyType(FromElementType.java:393) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.tree.FromElement.getPropertyType(FromElement.java:512) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.getDataType(DotNode.java:660) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.prepareLhs(DotNode.java:264) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.resolveInFunctionCall(DotNode.java:178) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.HqlSqlWalker.resolve(HqlSqlWalker.java:1030) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.expr(HqlSqlBaseWalker.java:1286) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.exprOrSubquery(HqlSqlBaseWalker.java:4699) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.functionCall(HqlSqlBaseWalker.java:2729) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.expr(HqlSqlBaseWalker.java:1361) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.exprOrSubquery(HqlSqlBaseWalker.java:4699) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.comparisonExpr(HqlSqlBaseWalker.java:4313) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2134) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2087) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2084) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2084) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2084) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2084) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:2062) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.whereClause(HqlSqlBaseWalker.java:813) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:607) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:311) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:259) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:261) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:189) ~[hibernate-core-5.2.8.Final.jar:5.2.8.Final]
... 148 common frames omitted
答案 0 :(得分:0)
尝试创建一个转换器,如下所示:
@Converter
public class SecureConverter implements AttributeConverter<SecureString, String>
{
@Override
public String convertToDatabaseColumn(SecureString ss) {
return ss.getActualValue();
}
@Override
public SecureString convertToEntityAttribute(String s)
{
SecureString result = new SecureString();
result.setActualValue(s);
return result;
}
}
并在您的属性上使用它:
@Entity
public class Country implements Serializable
{
private static final long serialVersionUID = 1L;
@Id
private Long id;
@Converter(converter = Secureconverter.class)
private SecureString nationality;
// getters and setters
}