Java 带有参数和单引号的自定义HQL函数
我正试图在hibernate中编写一个自定义函数来使用ts_vector(postgres),目前为止我的代码是:Java 带有参数和单引号的自定义HQL函数,java,spring,spring-boot,jpa,hql,Java,Spring,Spring Boot,Jpa,Hql,我正试图在hibernate中编写一个自定义函数来使用ts_vector(postgres),目前为止我的代码是: public class PostgresSQLFTSFunction implements SQLFunction { static final Logger LOG = LogManager.getLogger(); @Override public boolean hasArguments() { return true;
public class PostgresSQLFTSFunction implements SQLFunction {
static final Logger LOG = LogManager.getLogger();
@Override
public boolean hasArguments() {
return true;
}
@Override
public boolean hasParenthesesIfNoArguments() {
return false;
}
@Override
public Type getReturnType(Type firstArgumentType, Mapping mapping) throws QueryException {
return new BooleanType();
}
@Override
public String render(Type firstArgumentType, List arguments, SessionFactoryImplementor factory) throws QueryException {
if (arguments == null || arguments.size() < 2) {
throw new IllegalArgumentException("The function must have at least 2 arguments");
}
String fragment, ftsConfig, field, value;
if (arguments.size() == 3) {
ftsConfig = (String) arguments.get(0);
field = (String) arguments.get(1);
value = (String) arguments.get(2);
fragment = "to_tsvector(" + ftsConfig + ", unaccent(" + field + ")) @@ to_tsquery(" + ftsConfig + ", unaccent(" + value + "))";
} else {
field = (String) arguments.get(0);
value = (String) arguments.get(1);
fragment = "to_tsvector(unaccent(" + field + ")) @@ " + "to_tsquery('" + value + ":*' )";
}
LOG.info(fragment);
return fragment;
}
}
Hibernate生成的输出查询是:
select city0_.id as id1_0_, city0_.created_at as created_2_0_, city0_.updated_at as updated_3_0_, city0_.version as version4_0_, city0_.lat as lat5_0_, city0_.lng as lng6_0_, city0_.name as name7_0_, city0_.state_id as state_id8_0_ from cities city0_ where to_tsvector(unaccent(city0_.name)) @@ to_tsquery('?:*' )=true
这里的问题是to_tsquery('?:*')
不会将问号转换为命名参数(cityName),因为它包含在单引号中,但此处的单引号是必需的,否则查询将无法工作
例如,有效的查询是:
select city0_.id as id1_0_, city0_.created_at as created_2_0_, city0_.updated_at as updated_3_0_, city0_.version as version4_0_, city0_.lat as lat5_0_, city0_.lng as lng6_0_, city0_.name as name7_0_, city0_.state_id as state_id8_0_ from cities city0_ where to_tsvector(unaccent(city0_.name)) @@ to_tsquery('vi:*')=true;
因此,在上面的示例中,cityName
问号应该由HQL翻译为“vi”。
我怎样才能做到这一点
谢谢 您是否使用扩展方言中的registerFunction注册了您的函数?我没有,我采用了另一种MetadataBuilderContributor方法。我刚刚用这个片段编辑了这个问题,谢谢!顺便说一句,函数正在被调用,问题是?被解释为文字,而不是变量,因为它在引号中。您是否使用扩展方言中的registerFunction注册了您的函数?我没有,我采用了其他MetadataBuilderContributor方法。我刚刚用这个片段编辑了这个问题,谢谢!顺便说一句,函数正在被调用,问题是?被解释为文字,而不是变量,因为它位于引号内。
select city0_.id as id1_0_, city0_.created_at as created_2_0_, city0_.updated_at as updated_3_0_, city0_.version as version4_0_, city0_.lat as lat5_0_, city0_.lng as lng6_0_, city0_.name as name7_0_, city0_.state_id as state_id8_0_ from cities city0_ where to_tsvector(unaccent(city0_.name)) @@ to_tsquery('?:*' )=true
select city0_.id as id1_0_, city0_.created_at as created_2_0_, city0_.updated_at as updated_3_0_, city0_.version as version4_0_, city0_.lat as lat5_0_, city0_.lng as lng6_0_, city0_.name as name7_0_, city0_.state_id as state_id8_0_ from cities city0_ where to_tsvector(unaccent(city0_.name)) @@ to_tsquery('vi:*')=true;