QueryDSL 和日期差异
QueryDSL and date diff
我正在尝试使用 QueryDSL 计算具有日期差异的用户年龄。
QPlayer $ = QPlayer.player;
BooleanBuilder builder = new BooleanBuilder();
builder.and(Expressions.dateOperation(Integer.class, Ops.DateTimeOps.DIFF_YEARS, Expressions.currentDate(), $.birthDate).between(3, 5));
playerRespository.findAll(builder);
但失败并出现此错误
Hibernate: select player0_.user_id as id1_31_, player0_1_.user_birthdate as user_bir2_31_, player0_1_.user_register_date as user_reg3_31_, player0_1_.user_delete_date as user_del4_31_, player0_1_.user_email as user_ema5_31_, player0_1_.user_first_name as user_fir6_31_, player0_1_.user_last_name as user_las7_31_, player0_1_.user_login as user_log8_31_, player0_1_.user_password as user_pas9_31_, player0_1_.user_status as user_st10_31_, player0_.player_description as player_d1_20_, player0_.player_height as player_h2_20_, player0_.player_picture as player_p3_20_, player0_.player_role as player_r4_20_, player0_.player_weight as player_w5_20_ from players player0_ inner join users player0_1_ on player0_.user_id=player0_1_.id where (diff_years(player0_1_.user_birthdate, current_date) between ? and ?) and (lower(player0_1_.user_first_name) like ? escape '!')
2015-07-19 14:22:16,881 [main] ERROR: org.hibernate.engine.jdbc.spi.SqlExceptionHelper - FUNCTION xxx.diff_years does not exist
使用 MYSQL 数据库或 HSQL 时都会出现此错误。
该代码有什么问题?
谢谢
diff_years 很遗憾,Querydsl JPA 尚不支持
如何使用 queryDsl 自定义 MYSQL 方言。我展示了如何将 datediff 用于 select 语句。
自定义查询请求(计算now和createdDate之间的差异):
public List<MyDto> get() {
JPAQuery<HotelShortDto> query = new JPAQuery<>(em, MySQLJPQLTemplates.DEFAULT)
.select(Projections.constructor(MyDto.class,
Expressions.dateOperation(Integer.class, Ops.DateTimeOps.DIFF_MINUTES, Expressions.currentDate(), myEntity.createdDate),
))
.from(myEntity)
return query.fetch();
}
在 MYSQL 函数中获取分钟差异是 TIMESTAMPDIFF(对于 H2 db datediff)
配置:
public class MySQLJPQLTemplates extends JPQLTemplates {
public static final MySQLJPQLTemplates DEFAULT = new MySQLJPQLTemplates();
public MySQLJPQLTemplates() {
this(DEFAULT_ESCAPE);
add(Ops.DateTimeOps.DIFF_MINUTES, "TIMESTAMPDIFF(MINUTE,{0},{1})");
}
public void reconfigureForH2() {
add(Ops.DateTimeOps.DIFF_MINUTES, "datediff(MINUTE,{0},{1})");
}
public MySQLJPQLTemplates(char escape) {
super(escape);
}
}
此外,TIMESTAMPDIFF 不是休眠的标准函数,因此需要注册
public class CustomMySQLDialect extends MySQL57Dialect {
public CustomMySQLDialect() {
super();
registerFunction("TIMESTAMPDIFF", new StandardSQLFunction("TIMESTAMPDIFF"));
}
}
和application.yaml
...
spring.jpa.database-platform=com.my.project.CustomMySQLDialect
...
用于在执行查询之前测试调用
MySQLJPQLTemplates.DEFAULT.reconfigureForH2();
我正在尝试使用 QueryDSL 计算具有日期差异的用户年龄。
QPlayer $ = QPlayer.player;
BooleanBuilder builder = new BooleanBuilder();
builder.and(Expressions.dateOperation(Integer.class, Ops.DateTimeOps.DIFF_YEARS, Expressions.currentDate(), $.birthDate).between(3, 5));
playerRespository.findAll(builder);
但失败并出现此错误
Hibernate: select player0_.user_id as id1_31_, player0_1_.user_birthdate as user_bir2_31_, player0_1_.user_register_date as user_reg3_31_, player0_1_.user_delete_date as user_del4_31_, player0_1_.user_email as user_ema5_31_, player0_1_.user_first_name as user_fir6_31_, player0_1_.user_last_name as user_las7_31_, player0_1_.user_login as user_log8_31_, player0_1_.user_password as user_pas9_31_, player0_1_.user_status as user_st10_31_, player0_.player_description as player_d1_20_, player0_.player_height as player_h2_20_, player0_.player_picture as player_p3_20_, player0_.player_role as player_r4_20_, player0_.player_weight as player_w5_20_ from players player0_ inner join users player0_1_ on player0_.user_id=player0_1_.id where (diff_years(player0_1_.user_birthdate, current_date) between ? and ?) and (lower(player0_1_.user_first_name) like ? escape '!')
2015-07-19 14:22:16,881 [main] ERROR: org.hibernate.engine.jdbc.spi.SqlExceptionHelper - FUNCTION xxx.diff_years does not exist
使用 MYSQL 数据库或 HSQL 时都会出现此错误。
该代码有什么问题?
谢谢
diff_years 很遗憾,Querydsl JPA 尚不支持
如何使用 queryDsl 自定义 MYSQL 方言。我展示了如何将 datediff 用于 select 语句。
自定义查询请求(计算now和createdDate之间的差异):
public List<MyDto> get() {
JPAQuery<HotelShortDto> query = new JPAQuery<>(em, MySQLJPQLTemplates.DEFAULT)
.select(Projections.constructor(MyDto.class,
Expressions.dateOperation(Integer.class, Ops.DateTimeOps.DIFF_MINUTES, Expressions.currentDate(), myEntity.createdDate),
))
.from(myEntity)
return query.fetch();
}
在 MYSQL 函数中获取分钟差异是 TIMESTAMPDIFF(对于 H2 db datediff)
配置:
public class MySQLJPQLTemplates extends JPQLTemplates {
public static final MySQLJPQLTemplates DEFAULT = new MySQLJPQLTemplates();
public MySQLJPQLTemplates() {
this(DEFAULT_ESCAPE);
add(Ops.DateTimeOps.DIFF_MINUTES, "TIMESTAMPDIFF(MINUTE,{0},{1})");
}
public void reconfigureForH2() {
add(Ops.DateTimeOps.DIFF_MINUTES, "datediff(MINUTE,{0},{1})");
}
public MySQLJPQLTemplates(char escape) {
super(escape);
}
}
此外,TIMESTAMPDIFF 不是休眠的标准函数,因此需要注册
public class CustomMySQLDialect extends MySQL57Dialect {
public CustomMySQLDialect() {
super();
registerFunction("TIMESTAMPDIFF", new StandardSQLFunction("TIMESTAMPDIFF"));
}
}
和application.yaml
...
spring.jpa.database-platform=com.my.project.CustomMySQLDialect
...
用于在执行查询之前测试调用
MySQLJPQLTemplates.DEFAULT.reconfigureForH2();