【发布时间】:2023-03-23 06:29:01
【问题描述】:
背景:在我的一个项目中,我正在使用 JUnit 在 Spring Batch 上做 component testing。这里的应用程序数据库是 MYSQL。在 Junit 测试执行中,我让数据源在
之间切换- MYSQL 和
- H2(jdbc:h2:mem:MYTESTDB;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE;MODE=MYSQL)
基于配置。 使用 MYSQL 作为数据源进行调试,使用 H2 在构建服务器中单独运行测试。
一切正常,直到在应用程序逻辑中我不得不使用带有 DATEDIFF 的查询。
问题:查询失败,
org.h2.jdbc.JdbcSQLException: SQL 语句中的语法错误
原因:即使通过H2 run on MySQL mode,它也使用了 H2 函数并且这些函数是不同的
MYSQL DATEDIFF definition is DATEDIFF(expr1,expr2)
e.g. SELECT DATEDIFF('2010-11-30 23:59:59','2010-12-31')
==> 1
H2 DATEDIFF definision is DATEDIFF(unitstring, expr1, expr2)
unitstring = { YEAR | YY | MONTH | MM | WEEK | DAY | DD | DAY_OF_YEAR
| DOY | HOUR | HH | MINUTE | MI | SECOND | SS | MILLISECOND | MS }
e.g. SELECT DATEDIFF(dd, '2010-11-30 23:59:59','2010-12-31')
==> 1
解决方案尝试并失败:我尝试编写自定义函数
package com.asela.util;
import java.lang.reflect.Field;
import java.sql.Date;
import java.time.temporal.ChronoUnit;
import java.util.Map;
import java.util.Objects;
import org.h2.expression.Function;
public class H2Function {
public static long dateDifference(Date date1, Date date2) {
Objects.nonNull(date1);
Objects.nonNull(date2);
return ChronoUnit.DAYS.between(date1.toLocalDate(), date2.toLocalDate());
}
}
并用 H2 设置它
DROP ALIAS IF EXISTS DATEDIFF;
CREATE ALIAS DATEDIFF FOR "com.asela.util.H2Function.dateDifference";
以上无法替换现有的 DATEDIFF 仍然失败
org.h2.jdbc.JdbcSQLException:函数别名“DATEDIFF”已经存在; SQL语句:
我可以尝试其他任何方法来完成这项工作吗?
【问题讨论】: