【问题标题】:Hibernate not able to register 'LIMIT' function of MySQL in custom dialectHibernate 无法在自定义方言中注册 MySQL 的“LIMIT”功能
【发布时间】:2023-11-25 14:27:02
【问题描述】:

我想为 Hibernate 编写一个自定义方言以支持 MYSQL 的 'LIMIT' 功能,但即使我注册了这样的功能

    public class SiddheyMySQL57InnoDBDialect extends 
        MySQL57InnoDBDialect {

            public SiddheyMySQL57InnoDBDialect(){
            super();
            registerFunction("LIMIT",
            new SQLFunctionTemplate(StandardBasicTypes.INTEGER, "limit ?1"));
            registerFunction("MATCH", new SQLFunctionTemplate(
            StandardBasicTypes.INTEGER, "match(?1) against  (?2 in boolean mode)"));
  }

}

但是当我用 HQL 编写这个查询时,hibernate 给了我一个异常

     @Query("SELECT p FROM #{#entityName} p LIMIT(1)")
   List<Product> getLimitedProducts(@Param("name") final String name);

是的,我在 application.properties 中添加了自定义方言的路径

【问题讨论】:

    标签: java spring hibernate hql jpql


    【解决方案1】:

    这不是您使用 JPA 和 Hibernate 进行分页的方式。 LIMIT 是 MySQL 和 PostgreSQL 特定的关键字,而不是 JPQL。

    更多,LIMIT(1) 在 MySQL 中无效,因为 LIMIT 不是函数。您应该在原生 SQL 查询中使用它而不是 LIMIT 1,而不是在 JPQL 查询中。

    所以,你需要使用setMaxResults方法:

    List<Product> products = entityManager.createQuery("""
        SELECT p
        FROM Product p
        ORDER BY p.created_on DESC
        """, Product.class)
    .setMaxResults(50)
    .getResultList();
    

    您没有在查询中使用ORDER BY,这也是错误的,因为除非您使用ORDER BY,否则无法保证订单。

    【讨论】: