3

我的问题是关于

  1. 在 Hibernate 查询语言中使用注册函数进行日期/时间操作和
  2. IntelliJ IDEA 对 HQL 中这些注册函数的代码检查。

我使用带有 Java 7 的 Hibernate 4.2.5,SQL Server 2008 R2 作为数据库,以及 IntelliJ IDEA 12.1.6。

在 HQL 查询中,我需要执行 TSQL DATEADD 函数 - 或等效的 HQL 日期操作。这似乎不存在。

这是我想要实现的目标:

update MyTable set startTime = GETDATE(), targetTime = DATEADD(HOUR, allocatedTime, GETDATE()), endTime = null where faultReport.faultReportId = :faultReportId and slaTypeId = :slaTypeId

令人失望的是,在线搜索答案毫无帮助,最常见的建议(如此处看到的评论:https ://stackoverflow.com/a/18150333/2753571 )似乎是“不要在 hql 中使用日期操作”。在一般情况下(例如,当您想根据多行中另一列中的值更新一列时),我看不到如何绕过在 SQL 语句中执行操作。

与这篇文章中的建议类似:HQL 中的日期操作,我继承了 SQLServerDialect 实现并注册了新函数:

registerFunction("get_date", new NoArgSQLFunction("GETDATE", StandardBasicTypes.TIMESTAMP)); // this function is a duplication of "current_timestamp" but is here for testing / illustration
registerFunction("add_hours", new VarArgsSQLFunction(TimestampType.INSTANCE, "DATEADD(HOUR,", ",", ")"));

并将此属性添加到我的 persistence.xml:

<property name="hibernate.dialect" value="my.project.dialect.SqlServerDialectExtended" />

然后我用一个简单的(无意义的,承认的)查询进行测试,如下所示:

select x, get_date(), add_hours(1, get_date()) from MyTable x

这些函数似乎已成功注册,并且该查询似乎正在工作,因为生成了以下 SQL 并且结果正确:

select
    faultrepor0_.FaultReportSLATrackingId as col_0_0_,
    GETDATE() as col_1_0_,
    DATEADD(HOUR,
    1,
    GETDATE()) as col_2_0_,
    ... etc.

但是我现在遇到了 IntelliJ IDEA 的这个问题:在 HQL 中使用 get_date() 的地方,代码检查抱怨“<expression> expected, got ')'”。这被标记为错误,文件以红色标记为编译失败。

有人可以解释一下如何处理这个问题,或者解释一下更好的方法是什么?我是否使用了不正确的 SQLFunction 模板 (VarArgsSQLFunction)?如果是,哪个是最好用的?

我希望注册函数的使用不会在我的 IDE 中被标记为无效。理想情况下,如果有人可以提出比创建新的方言子类更好的方法,那就太棒了。

4

0 回答 0