Differenze tra le versioni di "Programmazione:Java/JDBC/MSSQL stored procedure"
(Creata pagina con 'A partire dalla versione 1.2 del driver JDBC Microsoft, la chiamata ad una stored procedure che ritorna in ResultSet, genera una eccezione del tipo "The statement did not return …') |
|||
Riga 23: | Riga 23: | ||
* This utility method is designed to work around the complexity of retrieving result sets from stored procedures in | * This utility method is designed to work around the complexity of retrieving result sets from stored procedures in | ||
* Microsoft SQL Server databases using the Microsoft JDBC driver 1.2.xx and later, where calling | * Microsoft SQL Server databases using the Microsoft JDBC driver 1.2.xx and later, where calling | ||
− | * | + | * Statement.executeQuery() with this driver throws an exception saying "The statement did not return a |
* result set". | * result set". | ||
* <p/> | * <p/> |
Versione delle 12:46, 24 set 2009
A partire dalla versione 1.2 del driver JDBC Microsoft, la chiamata ad una stored procedure che ritorna in ResultSet, genera una eccezione del tipo "The statement did not return a result set"
CallableStatement cs = conn.prepareCall("{CALL prSomeProcedure()}");
ResultSet rs = cs.executeQuery(); // Exception thrown here: "The statement did not return a result set".
La soluzione del problema sta nel rimpiazzare il codice sopra-indicato con questo:
CallableStatement cs = conn.prepareCall("{CALL prSomeProcedure()}");
ResultSet rs = DBUtil.executeStatementAndRetrieveResultSet(cs); // Exception not thrown here :)
dove il blocco di codice che ottiene il ResultSet è il seguente:
/**
* Executes a callable statement which has been prepared to call a stored procedure which returns a result set, and
* returns the first result set found.
*
* This utility method is designed to work around the complexity of retrieving result sets from stored procedures in
* Microsoft SQL Server databases using the Microsoft JDBC driver 1.2.xx and later, where calling
* Statement.executeQuery() with this driver throws an exception saying "The statement did not return a
* result set".
*
* This exception is due to this version (and later) of the driver returning additional update counts before
* returning a result set, thus requiring getMoreResults()
to be called in client code one or more
* times before the result set can be accessed. This method calls getMoreResults()
as necessary until
* the result set becomes accessible.
*
* @param cs A callable statement which has been prepared to call a stored procedure which returns a result set.
*
* @return The first (or only) result set returned by the statement.
* @throws IllegalArgumentException If the callable statement specified is null.
* @throws SQLException If any error occurs.
*/
protected ResultSet executeStatementAndRetrieveResultSet(CallableStatement cs) throws SQLException {
if (cs == null) {
throw new IllegalArgumentException("The callable statement specified was null.");
}
// Execute the statement...
boolean resultSetFound;
try {
resultSetFound = cs.execute();
}
catch (Exception e) {
SQLException sqle = new SQLException("Failed to execute the statement: " + e);
sqle.initCause(e);
throw sqle;
}
// Retrieve the first result set from the statement...
try {
while (!resultSetFound) {
resultSetFound = cs.getMoreResults();
// Check if there are no more results...
if (!resultSetFound && cs.getUpdateCount() == -1) {
// No more result sets are available. Stop searching...
break;
}
// Else continue looking for a result set...
}
if (resultSetFound) {
ResultSet rs = cs.getResultSet();
if (rs == null) {
throw new IllegalStateException("Unexpectedly failed to retrieve a result set from statement.");
}
return rs;
}
else {
throw new SQLException("Scanned all results returned by the statement but did not find a result set.");
}
}
catch (Exception e) {
SQLException sqle = new SQLException("Executed the statement but failed to retrieve a result set: " + e);
sqle.initCause(e);
throw sqle;
}
}