/** * Translate the given {@link SQLException} into a generic {@link DataAccessException}. * @param task readable text describing the task being attempted * @param sql the SQL query or update that caused the problem (may be {@code null}) * @param ex the offending {@code SQLException} * @return a DataAccessException wrapping the {@code SQLException} (never {@code null}) * @since 5.0 * @see #getExceptionTranslator() */ protected DataAccessException translateException(String task, @Nullable String sql, SQLException ex) { DataAccessException dae = getExceptionTranslator().translate(task, sql, ex); return (dae != null ? dae : new UncategorizedSQLException(task, sql, ex)); }
/** * Pre-checks the arguments, calls {@link #doTranslate}, and invokes the * {@link #getFallbackTranslator() fallback translator} if necessary. */ @Override @NonNull public DataAccessException translate(String task, @Nullable String sql, SQLException ex) { Assert.notNull(ex, "Cannot translate a null SQLException"); DataAccessException dae = doTranslate(task, sql, ex); if (dae != null) { // Specific exception match found. return dae; } // Looking for a fallback... SQLExceptionTranslator fallback = getFallbackTranslator(); if (fallback != null) { dae = fallback.translate(task, sql, ex); if (dae != null) { // Fallback exception match found. return dae; } } // We couldn't identify it more precisely. return new UncategorizedSQLException(task, sql, ex); }
/** * Moves the cursor in the ResultSet to the position specified by the row * parameter by traversing the ResultSet. * @param row The index of the row to move to */ private void moveCursorToRow(int row) { try { int count = 0; while (row != count && rs.next()) { count++; } } catch (SQLException se) { throw getExceptionTranslator().translate("Attempted to move ResultSet to last committed row", getSql(), se); } }
private void checkTranslation(SQLExceptionTranslator sext, int errorCode, Class<?> exClass) { SQLException sex = new SQLException("", "", errorCode); DataAccessException ex = sext.translate("", "", sex); assertTrue(exClass.isInstance(ex)); assertTrue(ex.getCause() == sex); }
/** * Convert the given HibernateException to an appropriate exception from the * {@code org.springframework.dao} hierarchy. * <p>Will automatically apply a specified SQLExceptionTranslator to a * Hibernate JDBCException, otherwise rely on Hibernate's default translation. * @param ex the HibernateException that occurred * @return a corresponding DataAccessException * @see SessionFactoryUtils#convertHibernateAccessException */ protected DataAccessException convertHibernateAccessException(HibernateException ex) { if (this.jdbcExceptionTranslator != null && ex instanceof JDBCException) { JDBCException jdbcEx = (JDBCException) ex; DataAccessException dae = this.jdbcExceptionTranslator.translate( "Hibernate operation: " + jdbcEx.getMessage(), jdbcEx.getSQL(), jdbcEx.getSQLException()); if (dae != null) { throw dae; } } return SessionFactoryUtils.convertHibernateAccessException(ex); }
@Test public void dataAccessResourceException() { SQLException dataAccessResourceEx = SQLExceptionSubclassFactory.newSQLDataException("", "", 2); DataAccessException dae = sext.translate("task", "SQL", dataAccessResourceEx); assertEquals(dataAccessResourceEx, dae.getCause()); assertThat(dae, instanceOf(TransientDataAccessResourceException.class)); }
protected void initializeConnection() { Assert.state(getDataSource() != null, "DataSource must not be null."); try { if (useSharedExtendedConnection) { if (!(getDataSource() instanceof ExtendedConnectionDataSourceProxy)) { throw new InvalidDataAccessApiUsageException( "You must use a ExtendedConnectionDataSourceProxy for the dataSource when " + "useSharedExtendedConnection is set to true."); } this.con = DataSourceUtils.getConnection(dataSource); ((ExtendedConnectionDataSourceProxy)dataSource).startCloseSuppression(this.con); } else { this.con = dataSource.getConnection(); } this.initialConnectionAutoCommit = this.con.getAutoCommit(); if (this.connectionAutoCommit != null && this.con.getAutoCommit() != this.connectionAutoCommit) { this.con.setAutoCommit(this.connectionAutoCommit); } } catch (SQLException se) { close(); throw getExceptionTranslator().translate("Executing query", getSql(), se); } }
@Test public void badSqlGrammarException() { SQLException badSqlGrammarExceptionEx = SQLExceptionSubclassFactory.newSQLDataException("", "", 1); DataAccessException dae = sext.translate("task", "SQL", badSqlGrammarExceptionEx); assertEquals(badSqlGrammarExceptionEx, dae.getCause()); assertThat(dae, instanceOf(BadSqlGrammarException.class)); }
@Test public void dataTruncationTranslation() { SQLExceptionTranslator sext = new SQLErrorCodeSQLExceptionTranslator(ERROR_CODES); SQLException dataAccessEx = new SQLException("", "", 5); DataTruncation dataTruncation = new DataTruncation(1, true, true, 1, 1, dataAccessEx); DataAccessResourceFailureException daex = (DataAccessResourceFailureException) sext.translate("task", "SQL", dataTruncation); assertEquals(dataTruncation, daex.getCause()); }
private void doTest(String sqlState, Class<?> dataAccessExceptionType) { SQLException ex = new SQLException(REASON, sqlState); SQLExceptionTranslator translator = new SQLStateSQLExceptionTranslator(); DataAccessException dax = translator.translate(TASK, SQL, ex); assertNotNull("Translation must *never* result in a null DataAccessException being returned.", dax); assertEquals("Wrong DataAccessException type returned as the result of the translation", dataAccessExceptionType, dax.getClass()); assertNotNull("The original SQLException must be preserved in the translated DataAccessException", dax.getCause()); assertSame("The exact same original SQLException must be preserved in the translated DataAccessException", ex, dax.getCause()); }
@Override protected void openCursor(Connection con) { try { if (isUseSharedExtendedConnection()) { preparedStatement = con.prepareStatement(sql, ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT); } else { preparedStatement = con.prepareStatement(sql, ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY); } applyStatementSettings(preparedStatement); if (this.preparedStatementSetter != null) { preparedStatementSetter.setValues(preparedStatement); } this.rs = preparedStatement.executeQuery(); handleWarnings(preparedStatement); } catch (SQLException se) { close(); throw getExceptionTranslator().translate("Executing query", getSql(), se); } }
/** * Convert the given HibernateException to an appropriate exception from the * {@code org.springframework.dao} hierarchy. * <p>Will automatically apply a specified SQLExceptionTranslator to a * Hibernate JDBCException, otherwise rely on Hibernate's default translation. * @param ex the HibernateException that occurred * @return a corresponding DataAccessException * @see SessionFactoryUtils#convertHibernateAccessException */ protected DataAccessException convertHibernateAccessException(HibernateException ex) { if (this.jdbcExceptionTranslator != null && ex instanceof JDBCException) { JDBCException jdbcEx = (JDBCException) ex; DataAccessException dae = this.jdbcExceptionTranslator.translate( "Hibernate operation: " + jdbcEx.getMessage(), jdbcEx.getSQL(), jdbcEx.getSQLException()); if (dae != null) { throw dae; } } return SessionFactoryUtils.convertHibernateAccessException(ex); }
SQLExceptionTranslator customTranslator = this.sqlErrorCodes.getCustomSqlExceptionTranslator(); if (customTranslator != null) { DataAccessException customDex = customTranslator.translate(task, sql, sqlEx); if (customDex != null) { return customDex;
/** * Read next row and map it to item, verify cursor position if * {@link #setVerifyCursorPosition(boolean)} is true. */ @Override protected T doRead() throws Exception { if (rs == null) { throw new ReaderNotOpenException("Reader must be open before it can be read."); } try { if (!rs.next()) { return null; } int currentRow = getCurrentItemCount(); T item = readCursor(rs, currentRow); verifyCursorPosition(currentRow); return item; } catch (SQLException se) { throw getExceptionTranslator().translate("Attempt to process next row failed", getSql(), se); } }
@Test public void errorCodeTranslation() { SQLExceptionTranslator sext = new SQLErrorCodeSQLExceptionTranslator(ERROR_CODES); SQLException badSqlEx = new SQLException("", "", 1); BadSqlGrammarException bsgex = (BadSqlGrammarException) sext.translate("task", "SQL", badSqlEx); assertEquals("SQL", bsgex.getSql()); assertEquals(badSqlEx, bsgex.getSQLException()); SQLException invResEx = new SQLException("", "", 4); InvalidResultSetAccessException irsex = (InvalidResultSetAccessException) sext.translate("task", "SQL", invResEx); assertEquals("SQL", irsex.getSql()); assertEquals(invResEx, irsex.getSQLException()); checkTranslation(sext, 5, DataAccessResourceFailureException.class); checkTranslation(sext, 6, DataIntegrityViolationException.class); checkTranslation(sext, 7, CannotAcquireLockException.class); checkTranslation(sext, 8, DeadlockLoserDataAccessException.class); checkTranslation(sext, 9, CannotSerializeTransactionException.class); checkTranslation(sext, 10, DuplicateKeyException.class); SQLException dupKeyEx = new SQLException("", "", 10); DataAccessException dksex = sext.translate("task", "SQL", dupKeyEx); assertTrue("Not instance of DataIntegrityViolationException", DataIntegrityViolationException.class.isAssignableFrom(dksex.getClass())); // Test fallback. We assume that no database will ever return this error code, // but 07xxx will be bad grammar picked up by the fallback SQLState translator SQLException sex = new SQLException("", "07xxx", 666666666); BadSqlGrammarException bsgex2 = (BadSqlGrammarException) sext.translate("task", "SQL2", sex); assertEquals("SQL2", bsgex2.getSql()); assertEquals(sex, bsgex2.getSQLException()); }
@Test public void batchExceptionTranslation() { SQLExceptionTranslator sext = new SQLErrorCodeSQLExceptionTranslator(ERROR_CODES); SQLException badSqlEx = new SQLException("", "", 1); BatchUpdateException batchUpdateEx = new BatchUpdateException(); batchUpdateEx.setNextException(badSqlEx); BadSqlGrammarException bsgex = (BadSqlGrammarException) sext.translate("task", "SQL", batchUpdateEx); assertEquals("SQL", bsgex.getSql()); assertEquals(badSqlEx, bsgex.getSQLException()); }
DataIntegrityViolationException divex = (DataIntegrityViolationException) sext.translate("task", "SQL", dataIntegrityViolationEx); assertEquals(dataIntegrityViolationEx, divex.getCause()); InvalidDataAccessApiUsageException idaex = (InvalidDataAccessApiUsageException) sext.translate("task", "SQL", featureNotSupEx); assertEquals(featureNotSupEx, idaex.getCause()); DataIntegrityViolationException divex2 = (DataIntegrityViolationException) sext.translate("task", "SQL", dataIntegrityViolationEx2); assertEquals(dataIntegrityViolationEx2, divex2.getCause()); PermissionDeniedDataAccessException pdaex = (PermissionDeniedDataAccessException) sext.translate("task", "SQL", permissionDeniedEx); assertEquals(permissionDeniedEx, pdaex.getCause()); DataAccessResourceFailureException darex = (DataAccessResourceFailureException) sext.translate("task", "SQL", dataAccessResourceEx); assertEquals(dataAccessResourceEx, darex.getCause()); BadSqlGrammarException bsgex2 = (BadSqlGrammarException) sext.translate("task", "SQL2", badSqlEx2); assertEquals("SQL2", bsgex2.getSql()); assertEquals(badSqlEx2, bsgex2.getSQLException()); ConcurrencyFailureException cfex = (ConcurrencyFailureException) sext.translate("task", "SQL", tranRollbackEx); assertEquals(tranRollbackEx, cfex.getCause()); TransientDataAccessResourceException tdarex = (TransientDataAccessResourceException) sext.translate("task", "SQL", transientConnEx); assertEquals(transientConnEx, tdarex.getCause()); QueryTimeoutException tdarex2 = (QueryTimeoutException) sext.translate("task", "SQL", transientConnEx2); assertEquals(transientConnEx2, tdarex2.getCause()); RecoverableDataAccessException rdaex2 = (RecoverableDataAccessException) sext.translate("task", "SQL", recoverableEx);
throw getExceptionTranslator().translate("Executing stored procedure", getSql(), se);
if (this.jdbcExceptionTranslator != null && ex instanceof JDBCException) { JDBCException jdbcEx = (JDBCException) ex; DataAccessException dae = this.jdbcExceptionTranslator.translate( "Hibernate operation: " + jdbcEx.getMessage(), jdbcEx.getSQL(), jdbcEx.getSQLException()); if (dae != null) {
if (this.jdbcExceptionTranslator != null && ex instanceof JDBCException) { JDBCException jdbcEx = (JDBCException) ex; DataAccessException dae = this.jdbcExceptionTranslator.translate( "Hibernate operation: " + jdbcEx.getMessage(), jdbcEx.getSQL(), jdbcEx.getSQLException()); if (dae != null) {