处理Spring JdbcTemplate的batchUpdate错误

8
我正在尝试使用batchUpdate更新表中的数千行。我的要求如下:
1) 假设每个批次有1000条记录。第235条记录引起了错误。我该如何找出引起错误的记录。
2) 假设第600条记录没有更新(原因可能是没有符合where子句的记录)。如何找出未更新的记录。
3) 在上述两种情况下,如何继续处理剩余的记录。
2个回答

7

经过长时间的搜索和调试,唯一的解决方案是转到BatchUpdateException类并找到负元素,从MAP中推断出插入错误的值。

import java.sql.BatchUpdateException;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.List;
import java.util.Map;


import org.springframework.jdbc.core.BatchPreparedStatementSetter;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;


@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
@Repository("dao_")
public class YouDao extends CommunDao implements IyouDao {

    public void bulkInsert(final List<Map<String, String>> map)
            throws BusinessException { 
        try {

            String sql = " insert into  your_table " + "(  aa,bb  )"
                    + "values " + "(  ?,? )";
            BatchPreparedStatementSetter batchPreparedStatementSetter = new BatchPreparedStatementSetter() {
                @Override
                public void setValues(PreparedStatement ps, int i)
                        throws SQLException {
                    Map<String, String> bean = map.get(i);

                    ps.setString(1, bean.get("aa"));
                    ps.setString(2, bean.get("bb")); 
                    //..
                    //..

                }

                @Override
                public int getBatchSize() {
                    return map.size();
                }
            };

             getJdbcTemplate().batchUpdate(sql, batchPreparedStatementSetter);

        }

        catch (Exception e) {
            if (e.getCause() instanceof BatchUpdateException) {
                BatchUpdateException be = (BatchUpdateException) e.getCause();
                int[] batchRes = be.getUpdateCounts();
                if (batchRes != null && batchRes.length > 0) {
                    for (int index = 0; index < batchRes.length; index++) {
                        if (batchRes[index] == Statement.EXECUTE_FAILED) {
                            logger.error("Error execution >>>>>>>>>>>"
                                    + index + " --- , codeFail : " + batchRes[index]
                                    + "---, line " + map.get(index));
                        }
                    }
                }
            }  
            throw new BusinessException(e);
        }

    }

}

我看到你正在捕获BatchUpdateException,但是当我尝试这样做时,我会得到一个语法错误,因为它说try块中没有任何类实际抛出它,而文档也证实了这一点。是什么引发了你的异常?(这就是你在使用getCause()的原因吗?) - Steve
@halfer 我尝试做同样的事情,但我没有得到批量更新异常本身,你能帮我解决一下吗?https://dev59.com/wb7pa4cB1Zd3GeqP7-Fq - Sameer
2
@Sameer:我是这个答案的编辑 - 我认为你的问题是对 question_maven_com 的。然而,他们已经11个月没有登录了。 - halfer

-4
int[] rows =jdbcTemplate.batchUpdate(TbCareQueryConstant.SQL_UPDATE_BANKDETAILS_OF_USER, new BatchPreparedStatementSetter(){

.....
your code


}

 for(int i=0 ; i < rows.length ; i++){
        
     if(rows[i] == 0){
         
           
        }       
    }

4
欢迎来到 Stack Overflow!您的回答只包含(格式不良的)代码,缺少解释。我建议您阅读《如何撰写好答案》并考虑编辑您的答案。 - FanaticD
这似乎是一个不完整的答案,比LQ更糟糕。我试图在此上提出NAA标志,但被拒绝了。 - halfer

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接