You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多
文档控制台
免费开始使用

使用Spring MVC JdbcTemplate查询数据库时遇DataIntegrityViolationException求助

解决JdbcTemplate查询时的DataIntegrityViolationException(列索引越界)问题

嘿,这个问题我之前排查过类似的,咱们先从异常信息入手拆解:

org.springframework.dao.DataIntegrityViolationException: PreparedStatementCallback; SQL [select * from cyberabadpolice where fir_date between '2020-01-01' and '2020-12-31' and current_status='UI']; The column index is out of range: 1, number of columns: 0.; nested exception is org.postgresql.util.PSQLException: The column index is out of range: 1, number of columns: 0.

这个异常的核心是PostgreSQL驱动找不到你要绑定的参数位置——你提到业务需要接收用户的两个输入参数,但你的SQL语句里全是硬编码的固定值('2020-01-01''2020-12-31''UI'),没有预留任何参数占位符?。当你调用JdbcTemplate的查询方法并传入用户参数时,框架会尝试把参数绑定到SQL的第1个占位符上,但SQL里根本没有?,自然就报“列索引越界”了。

正确的解决步骤:

  1. 用占位符替换SQL中的硬编码参数
    根据你需要接收的两个用户输入参数,调整SQL语句,用?代替固定值。比如:

    • 如果两个参数是「起始日期」和「结束日期」:
      select * from cyberabadpolice where fir_date between ? and ?
      
    • 如果两个参数是「指定日期范围」和「当前状态」:
      select * from cyberabadpolice where fir_date between '2020-01-01' and '2020-12-31' and current_status = ?
      

    (根据你的实际业务需求选择对应写法,核心是把用户输入的部分换成?

  2. 调用JdbcTemplate时传入对应参数
    确保参数的数量、顺序和SQL里的占位符完全匹配,示例代码如下:

    // 假设你的实体类是CyberabadPolice
    String sql = "select * from cyberabadpolice where fir_date between ? and ?";
    List<CyberabadPolice> result = jdbcTemplate.query(
        sql,
        new Object[]{userInputStartDate, userInputEndDate}, // 对应用户输入的两个参数
        new BeanPropertyRowMapper<>(CyberabadPolice.class)
    );
    

额外提醒:

  • 千万别直接在SQL里拼接用户输入的字符串,不仅容易触发这类参数绑定错误,还会带来SQL注入的安全风险,用占位符是最安全规范的做法。
  • 这里的DataIntegrityViolationException有点误导人,它本质不是数据库数据完整性的问题(比如主键冲突、非空约束违反),而是底层JDBC PreparedStatement的参数绑定失败导致的,根源是SQL写法不对。

内容的提问来源于stack exchange,提问作者Mantramurthy saishankar

火山引擎 最新活动