列名异常无效 - 带别名的JdbcPagingItemReader查询

时间:2018-04-10 20:19:48

标签: java spring-boot jdbc spring-batch

当JdbcPagingItemReader查询具有连接和别名时,

Spring批处理步骤失败。当我删除联接并从employee表执行简单查询时,它工作正常。以下是失败的代码段。有人遇到过这样的问题吗?任何帮助,将不胜感激。

弹簧分批芯4.0.1.RELEASE 弹簧引导2.0.0.RELEASE

@Autowired
    @Bean(destroyMethod = "")
    @StepScope
    public JdbcPagingItemReader<String> dbItemReader(final DataSource dataSource, final PreparedStatementSetter paramSetter) {
         return new JdbcPagingItemReaderBuilder<String>().name("dbReader").dataSource(dataSource)            .queryProvider(queryProvider(prodDataSource)).rowMapper((rs, rowNum) -> {
         return rs.getString("first_name");
         }).pageSize(1000).fetchSize(1000).build();
    }

@Bean
public PagingQueryProvider queryProvider(final DataSource dataSource) {
    final OraclePagingQueryProvider provider = new OraclePagingQueryProvider();
    provider.setSelectClause("select first_name");
    provider.setFromClause("from employee e join department d on e.dept_no= d.dept_no");
    provider.setWhereClause("where d.dept_name in ('HR','Marketing')");
    final Map<String, Order> sortKeys = new HashMap<String, Order>();
    sortKeys.put("e.dept_no", Order.ASCENDING);
    sortKeys.put("e.employee_id", Order.ASCENDING);
    provider.setSortKeys(sortKeys);
    try {
        return provider;
    } catch (final Exception e) {
        e.printStackTrace();
        return null;
    }
}
  

引起:java.sql.SQLException:列名无效   oracle.jdbc.driver.OracleStatement.getColumnIndex(OracleStatement.java:3965)   〜[ojdbc6-11.2.0.3.jar:12.1.0.1.0] at   oracle.jdbc.driver.InsensitiveScrollableResultSet.findColumn(InsensitiveScrollableResultSet.java:299)   〜[ojdbc6-11.2.0.3.jar:12.1.0.1.0] at   oracle.jdbc.driver.GeneratedResultSet.getObject(GeneratedResultSet.java:1394)   〜[ojdbc6-11.2.0.3.jar:12.1.0.1.0] at   org.apache.commons.dbcp.DelegatingResultSet.getObject(DelegatingResultSet.java:328)   〜[commons-dbcp-1.4.jar:1.4] at   org.apache.commons.dbcp.DelegatingResultSet.getObject(DelegatingResultSet.java:328)   〜[commons-dbcp-1.4.jar:1.4] at   org.springframework.batch.item.database.JdbcPagingItemReader $ PagingRowMapper.mapRow(JdbcPagingItemReader.java:333)   〜[spring-batch-infrastructure-4.0.0.RELEASE.jar:4.0.0.RELEASE] at   org.springframework.jdbc.core.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:93)   〜[spring-jdbc-5.0.4.RELEASE.jar:5.0.4.RELEASE] at   org.springframework.jdbc.core.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:60)   〜[spring-jdbc-5.0.4.RELEASE.jar:5.0.4.RELEASE] at   org.springframework.jdbc.core.JdbcTemplate $ 1.doInPreparedStatement(JdbcTemplate.java:667)   〜[spring-jdbc-5.0.4.RELEASE.jar:5.0.4.RELEASE] at   org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:605)   〜[spring-jdbc-5.0.4.RELEASE.jar:5.0.4.RELEASE] ... 72个常用帧   省略

3 个答案:

答案 0 :(得分:1)

几年后,我偶然发现了同样的问题。 我想给出正确答案,因为这里没有完全设置正确答案。

@Bean
public PagingQueryProvider queryProvider(final DataSource dataSource) {
    final OraclePagingQueryProvider provider = new OraclePagingQueryProvider();
    provider.setSelectClause("select e.first_name, e.dept_no as dept_no, e.employee_id as employee_id");
    provider.setFromClause("from employee e join department d on e.dept_no= d.dept_no");
    provider.setWhereClause("where d.dept_name in ('HR','Marketing')");
    final Map<String, Order> sortKeys = new HashMap<String, Order>();
    sortKeys.put("dept_no", Order.ASCENDING);
    sortKeys.put("employee_id", Order.ASCENDING);
    provider.setSortKeys(sortKeys);
    try {
        return provider;
    } catch (final Exception e) {
        e.printStackTrace();
        return null;
    }
}

有什么变化:

  • e.dept_no as dept_no, e.employee_id as employee_id 被添加到选择查询中。
  • sortKeys.put 不能使用别名。 问题是 sortKeys 将从结果列表中检索数据。
    如果您设置别名 => 行映射器尝试获取 alias.column_name 并且不存在,因为结果集不包含别名。
    因此,我们还在选择查询中默认添加了 AS,以避免列名不明确。

答案 1 :(得分:0)

我敢打赌,使用JOIN是行不通的,因为它是Page item阅读器。它需要一致的列表和主键才能起作用。您可以尝试使用自己唯一的主键创建JOIN作为视图,并针对该主键运行简单查询。

答案 2 :(得分:0)

don't use this (e.) -point- at your SortKeys order by experssion, and it will be fine