当前位置: 首页 > 知识库问答 >
问题:

使用Spring Boot@DataJpaTest中的投影对h2数据库选择查询执行“列计数不匹配”

南宫阳冰
2023-03-14

我有一个Spring-Boot应用程序,其中包含一些使用内容投影的本机查询。它在生产环境中运行Postgres并且运行良好。我正在尝试使用@DataJpaTest和h2内存数据库为存储库设置集成测试,但我使用内容投影的查询因驱动程序中的JdbcSQLException而失败:

org.h2.jdbc.JdbcSQLException:列计数不匹配

我成功保存到TestEntityManager,所以数据库中有记录,但是我无法通过存储库方法调用SELECT。它在Postgres的生产环境中正常工作——这是h2的限制吗?是否有我可以应用的解决方法,以便我可以正确测试它?

存储库方法看起来像这样(一个内连接,在where子句中的两个参数,表名和列更改以保护有罪):

public interface OrderRepository extends PagingAndSortingRepository<Order, Long> {

    @Query(nativeQuery = true,
           value = "SELECT order.id, order.total, pizza.name " +
                   "FROM example.order " +
                   "INNER JOIN example.pizza USING (pizza_id) " +
                   "WHERE order.customer_id = :custId " +
                   "AND order.order_date = :orderDate ",
           countQuery = "SELECT count(order.id) " +
                        "FROM example.order " +
                        "INNER JOIN example.pizza USING (pizza_id) " +
                        "WHERE order.customer_id = :custId " +
                        "AND order.order_date = :orderDate")
    <T> Page<T> findAllByCustIdAndOrderDate(String custId, OffsetDateTime orderDate, Pageable paging, Class<T> type);
}

投影如下所示:

public interface PizzaOrderProjection {
  Long getId();
  Double getTotal();
  String getName();
}

当我调用findAllByCustIdAndOrderDate时会触发异常,它打印的SQL语句导致它是SELECT。SELECT it prints看起来非常正常:

Hibernate: 
    /* dynamic native SQL query */ SELECT
        order.id,
        order.total,
        pizza.name 
    FROM
        example.order 
    INNER JOIN
        example.pizza USING (pizza_id) 
    WHERE
        order.customer_id = ? 
        AND order.order_date = ?  limit ?
2019-04-09 12:42:18.704  WARN 17568 --- [           main] o.h.engine.jdbc.spi.SqlExceptionHelper   : SQL Error: 21002, SQLState: 21S02
2019-04-09 12:42:18.708 ERROR 17568 --- [           main] o.h.engine.jdbc.spi.SqlExceptionHelper   : Column count does not match; SQL statement:

共有1个答案

芮朗
2023-03-14

事实证明,错误消息实际上与根本问题无关。

H2数据库不支持在内部连接子句上使用关键字,只支持关键字上的关键字。

通过将内部连接改为在上使用来解决此问题,如下所示:

public interface OrderRepository extends PagingAndSortingRepository<Order, Long> {

    @Query(nativeQuery = true,
           value = "SELECT order.id, order.total, pizza.name " +
                   "FROM example.order " +
                   "INNER JOIN example.pizza ON order.pizza_id = pizza.pizza_id " +
                   "WHERE order.customer_id = :custId " +
                   "AND order.order_date = :orderDate ",
           countQuery = "SELECT count(order.id) " +
                        "FROM example.order " +
                        "INNER JOIN example.pizza ON order.pizza_id = pizza.pizza_id " +
                        "WHERE order.customer_id = :custId " +
                        "AND order.order_date = :orderDate")
    <T> Page<T> findAllByCustIdAndOrderDate(String custId, OffsetDateTime orderDate, Pageable paging, Class<T> type);
}

这一更改使查询在postgres和h2中都有效。

 类似资料:
  • 问题内容: 我有一个关于MYSQL中的选择查询的问题 我有两个不同的表,我想获得一定的结果 我使用了COUNT方法,该方法只给我结果(> = 1) 但实际上,我想使用包含零的所有计数怎么做? 我的查询是: 第一张桌子:Content_hits 第二张表:Content_tag 结果但不完整 例如:tag_id = 1的Subsrciber6应该具有count(*)= 0 问题答案: 现在,您已经进

  • 问题内容: 我有一个Oracle表,其中包含一组范围(RangeA和RangeB)。这些列是varchar,因为它们可以同时容纳数字和字母数字值,如以下示例所示: 我需要执行一个查询,该查询仅返回具有数值的记录,并对该查询执行Count。到目前为止,我已经尝试过使用两个不同的查询来做到这一点,但没有任何运气: 查询1: 查询2: 子查询工作正常,因为我得到的两个记录都只有数字值,但是查询的COUN

  • 问题内容: 是否可以对位于同一服务器上的不同数据库进行选择(或插入)语句?如果是,怎么办? 问题答案: 您将使用以下语法指定数据库 例:

  • 我正在用Cucumber编写验收测试,我想使用H2数据库进行测试。 应用程序测试属性如下所示: 在目录resources/db/migration中,我有一个包含这些脚本的sql文件: 但是当我运行测试时,H2用默认格式创建模式,而不是使用脚本: 如您所见,所有VARCHAR都是使用255大小创建的,而不是真实值。 你能帮我把飞行道和H2整合起来吗? 谢谢!

  • 我正在使用Hibernate标准和投影来获得不同的值,如下所示: 我正在使用带有投影的结果转换器来获取不同值的列表

  • 问题内容: 我想测试某个代码段执行的SQL查询越少越好。 似乎有其自己的方法,它将做到这一点。但是由于我没有修补ActiveRecord,所以对我来说没什么用。 RSpec或ActiveRecord是否提供任何官方的公开方式来计算在代码块中执行的SQL查询的数量? 问题答案: 我认为您通过提及回答了您自己的问题,但是这里有: 我建议您看一下后面的代码,并使用它来构建自己的方法,该方法可用于计算查询