Hibernate 如何在Spring Boot应用程序中添加非标准sql函数?

Hibernate 如何在Spring Boot应用程序中添加非标准sql函数?,hibernate,spring-boot,spring-data-jpa,sql-function,Hibernate,Spring Boot,Spring Data Jpa,Sql Function,我的应用程序需要在Postgres、Mysql和Hsqldb之间可移植。我已经设置了Flyway,使一些自定义函数在这三个函数上都可用,现在我想在我的SQL/HQL查询中使用这些函数 我当前的设置是使用单独的方言s,在使用application-{profile}.yml之间切换;这是可行的,但函数声明需要在各种方言中重复,而且感觉不太理想 查看Hibernate文档,它说我应该使用org.Hibernate.cfg.Configuration#addSqlFunction(),这似乎更便于移植

我的应用程序需要在Postgres、Mysql和Hsqldb之间可移植。我已经设置了Flyway,使一些自定义函数在这三个函数上都可用,现在我想在我的SQL/HQL查询中使用这些函数

我当前的设置是使用单独的
方言
s,在使用
application-{profile}.yml之间切换;这是可行的,但函数声明需要在各种方言中重复,而且感觉不太理想

查看Hibernate文档,它说我应该使用
org.Hibernate.cfg.Configuration#addSqlFunction()
,这似乎更便于移植,并且不需要扩展所有三种方言

我的问题是:如何在我的Spring Boot(1.3)应用程序中访问Hibernate
配置
类?默认情况下没有要注入的bean,也没有
LocalSessionFactoryBean
bean


有人能告诉我正确的方向吗,或者以其他方式注册我的sql函数一次吗?

对于这个问题,我有相当多的技巧

Hibernate使用
org.Hibernate.dialogue.dialogue.SQLFunctionRegistry
识别DB函数

下面是hibernate core 4.3.10的一个示例。 在内部,它由两个私有字段组成:

/**
 * Defines a registry for SQLFunction instances
 *
 * @author Steve Ebersole
 */
public class SQLFunctionRegistry {
    private final Dialect dialect;
    private final Map<String, SQLFunction> userFunctions;
然后调用以下代码:

private void registerMyDbFunctions()
{
    SQLFunctionRegistry registry = this.emFactory.unwrap(org.hibernate.internal.SessionFactoryImpl.class).getSqlFunctionRegistry();
    Field field = ReflectionUtils.findField(SQLFunctionRegistry.class, "userFunctions");
    ReflectionUtils.makeAccessible(field);
    Map<String, SQLFunction> userFunctions = (Map<String, SQLFunction>)ReflectionUtils.getField(field, registry);

    userFunctions.put("my_func", new SQLFunctionTemplate(TextType.INSTANCE, "my_func(?1, ?2)"));
}
private void registerMyDbFunctions()
{
SQLFunctionRegistry=this.emFactory.unwrap(org.hibernate.internal.SessionFactoryImpl.class).getSqlFunctionRegistry();
Field=ReflectionUtils.findField(SQLFunctionRegistry.class,“userFunctions”);
ReflectionUtils.MakeAccessable(字段);
Map userFunctions=(Map)ReflectionUtils.getField(field,registry);
put(“my_func”,新的SQLFunctionTemplate(TextType.INSTANCE,“my_func(?1,?2)”);
}
由于
userFunctions
字段是私有的,并且未在类中公开,因此我使用ReflectionUtils获取其值。它通常是空的,我只是将我的DB函数添加到其中

由于我必须进入
SqlFunctionRegistry
的内部,这是一种黑客行为,但我更喜欢它,而不是创建新的DB方言并弄乱它

private void registerMyDbFunctions()
{
    SQLFunctionRegistry registry = this.emFactory.unwrap(org.hibernate.internal.SessionFactoryImpl.class).getSqlFunctionRegistry();
    Field field = ReflectionUtils.findField(SQLFunctionRegistry.class, "userFunctions");
    ReflectionUtils.makeAccessible(field);
    Map<String, SQLFunction> userFunctions = (Map<String, SQLFunction>)ReflectionUtils.getField(field, registry);

    userFunctions.put("my_func", new SQLFunctionTemplate(TextType.INSTANCE, "my_func(?1, ?2)"));
}