/** @param sqe */ private void endException(int batchSize) { // Rollback if dbContext.getAutoCommit() is false try { dbContext.getDataConnection().rollback(); } catch (SQLException sqe) { logger.error( Messages.getFormattedString( "DatabaseDAO.sqlExceptionRollback", new String[] { String.valueOf(currentRowNumber + 1 - batchSize), String.valueOf(currentRowNumber + 1), dbContext.getDbConfigName(), sqe.getMessage() }), sqe); } }
/* * (non-Javadoc) * @see com.salesforce.dataloader.dao.DataWriter#writeRowList(java.util.List) */ @Override public boolean writeRowList(List<Row> inputRowList) throws DataAccessObjectException { // make sure that the update is setup and ready to go, otherwise stop if (!dbContext.isOpen()) { throw new DataAccessObjectInitializationException( Messages.getString("DatabaseDAO.errorUpdateNotOpen")); } boolean success = true; int startingRowNumber = currentRowNumber; try { // for batchsize = 1, don't do batching, this provides much better error output if (inputRowList.size() == 1) { dbContext.setSqlParamValues(sqlConfig, config, inputRowList.get(0)); currentRowNumber++; } else { // for each row set the Sql params in the prepared statement dbContext.getDataStatement().clearBatch(); for (Row inputRow : inputRowList) { dbContext.setSqlParamValues(sqlConfig, config, inputRow); dbContext.getDataStatement().addBatch(); currentRowNumber++; } } } catch (ParameterLoadException e) { throw new DataAccessObjectException(e.getMessage(), e); } catch (SQLException sqe) { String errMsg = Messages.getFormattedString( "DatabaseDAO.sqlExceptionPrepareRow", new String[] { String.valueOf(currentRowNumber + 1), String.valueOf(startingRowNumber + 1), String.valueOf(startingRowNumber + inputRowList.size() + 1), dbContext.getDbConfigName(), sqe.getMessage() }); logger.error(errMsg, sqe); // batch failed: set current row number to the end of the batch currentRowNumber = startingRowNumber + inputRowList.size(); throw new DataAccessObjectException(errMsg, sqe); } catch (Exception e) { String errMsg = Messages.getFormattedString( "DatabaseDAO.exceptionPrepareRow", new String[] { String.valueOf(currentRowNumber + 1), String.valueOf(startingRowNumber + 1), String.valueOf(startingRowNumber + inputRowList.size() + 1), dbContext.getDbConfigName(), e.getMessage() }); logger.error(errMsg, e); // batch failed: set current row number to the end of the batch currentRowNumber = startingRowNumber + inputRowList.size(); throw new DataAccessObjectException(errMsg, e); } try { // for batchsize = 1, don't do batching, this provides much better error output int totalSuccessRows = 0; if (inputRowList.size() == 1) { // non-batch update returns exception, so it's always success unless exception is returned dbContext.getDataStatement().executeUpdate(); success = true; totalSuccessRows = 1; } else { // execute the update SQL in batch int[] rowsUpdatedArray = dbContext.getDataStatement().executeBatch(); for (int rowsUpdated : rowsUpdatedArray) { if (rowsUpdated == PreparedStatement.SUCCESS_NO_INFO) { totalSuccessRows = rowsUpdatedArray.length; success = true; break; } } } logger.debug( Messages.getFormattedString( "DatabaseDAO.updatedStatus", new String[] {String.valueOf(totalSuccessRows), String.valueOf(currentRowNumber)})); // commit the change dbContext.getDataConnection().commit(); } catch (SQLException sqe) { if (sqe instanceof BatchUpdateException) { int[] updateCountArray = ((BatchUpdateException) sqe).getUpdateCounts(); for (int i = 0; i < updateCountArray.length; i++) { if (updateCountArray[i] == PreparedStatement.EXECUTE_FAILED) { // FIXME all results are the same, return success = false; break; } } } String errMsg = Messages.getFormattedString( "DatabaseDAO.sqlExceptionWriteRow", new String[] { String.valueOf(currentRowNumber + 1 - inputRowList.size()), String.valueOf(currentRowNumber + 1), dbContext.getDbConfigName(), sqe.getMessage() }); logger.error(errMsg, sqe); endException(inputRowList.size()); throw new DataAccessObjectException(errMsg, sqe); } catch (Exception e) { String errMsg = Messages.getFormattedString( "DatabaseDAO.exceptionWriteRow", new String[] { String.valueOf(currentRowNumber + 1 - inputRowList.size()), String.valueOf(currentRowNumber + 1), dbContext.getDbConfigName(), e.getMessage() }); logger.error(errMsg, e); endException(inputRowList.size()); throw new DataAccessObjectException(errMsg, e); } return success; }