gpt4 book ai didi

hibernate - 当使用 spring-data-jpa 2.6.2 的 java.sql.Timestamp 查询 IS NULL 时,hsqldb 中转换的不兼容数据类型

转载 作者:行者123 更新时间:2023-12-05 04:31:31 24 4
gpt4 key购买 nike

spring-boot-starter-data-jpa 2.6.4 依赖于 spring-data-jpa 2.6.2,后者依赖于 hsqldb 2.5.2 和 hibernate 5.6.7.Final

当我们想在 CrudRepository 中查询类型为 java.sql.Timestamp 的多个值时,即

@Query("SELECT dm " +
" FROM DataModel dm " +
"WHERE (dm.ts1 IS NULL OR :ts1 IS NULL OR dm.ts1 < :ts1) " +
" AND (dm.ts2 IS NULL OR :ts2 IS NULL OR dm.ts2 < :ts2)")
List<DataModel> findByTimestamps(@Param("ts1") Timestamp ts1, @Param("ts2") Timestamp ts2);

它失败了org.hsqldb.HsqlException:转换中不兼容的数据类型

spring-data-jpa 2.6.3 也会发生这种情况

降级到 hsqldb 2.5.1 有效

重现 repo : https://github.com/daveyx/spring-data-hsqldb-timestamp-issue

问题出现在 org.hsqldb.jdbc.JDBCPreparedStatement#setTimestamp(int, java.sql.Timestamp, java.util.Calendar) 中,因为参数类型错误。

在 JDBCPreparedStatement#setTimestamp 中,@Param 注释参数的“IS NULL”部分似乎导致“CharacterType”而不是“DateTimeType”。

最佳答案

如您所述,问题是由条件 OR :ts1 IS NULLOR :ts2 IS NULL 引起的。 Hibernate 以 ? 的形式将这些应用于 SQL 查询。 IS NULL 并且 HSQLDB 将参数解析为字符串。 Hibernate 然后假定参数类型已解析为 java.sql.Timestamp 并调用 setTimestamp(int, Timestamp) 方法,这导致了问题。

您可以添加 CAST 来确定参数的类型。

@Query("SELECT dm " +
" FROM DataModel dm " +
"WHERE (dm.ts1 IS NULL OR CAST(:ts1 AS TIMESTAMP) IS NULL OR dm.ts1 < :ts1) " +
" AND (dm.ts2 IS NULL OR CAST(:ts2 AS TIMESTAMP) IS NULL OR dm.ts2 < :ts2)")

HSQLDB 版本 2.5.1 对 setTimestamp(int, Timestamp) 很宽松,当目标不是时间戳时将时间戳转换为字符串。版本 2.5.2 和 2.6.0 中的回归使其变得严格。 HSQLDB 的 future 版本将恢复为宽松的方法。

关于hibernate - 当使用 spring-data-jpa 2.6.2 的 java.sql.Timestamp 查询 IS NULL 时,hsqldb 中转换的不兼容数据类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/71836247/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com