Opération non autorisée : exception fermée ResultSet en Java
Lors de l'exécution de certaines requêtes SQL, les développeurs peuvent rencontrer une "java.sql.SQLException : Opération non autorisée après la fermeture de ResultSet. Cette erreur se produit généralement lorsque plusieurs ResultSets sont tentés simultanément à partir du même objet Statement.
Considérez l'extrait de code suivant qui illustre ce problème :
// Problem code: using the same statement object to create multiple ResultSets try { // Execute the first query and obtain ResultSet rs ResultSet rs = statement.executeQuery("SELECT `name` FROM `user` WHERE `id` = " + userId + " LIMIT 1;"); // Execute the second query and obtain ResultSet rs2 ResultSet rs2 = statement.executeQuery("SELECT `id` FROM `profiles` WHERE `id` =" + profId + ";"); // Prepare a new statement and attempt to use rs2 PreparedStatement pst = (PreparedStatement)connection.prepareStatement("INSERT INTO `blah`............"); // Process data from rs2 and update the database using pst while(rs2.next()) { int id = rs2.getInt("id"); int stuff = getStuff(id); pst.setInt(1, stuff); pst.addBatch(); } pst.executeBatch(); } catch (Exception e) { e.printStackTrace(); }
Dans ce code, deux ResultSets (rs et rs2) sont créés à partir du même objet Statement (instruction). Cependant, bien que rs ne soit pas explicitement fermé, il l'est implicitement lorsque la deuxième requête est exécutée et que rs2 est obtenu. Cela entraîne une exception car rs2 tente de fonctionner sur un ResultSet fermé.
Résolution :
Pour résoudre ce problème, il est crucial de fermer tous les ResultSets avant d'utiliser le même objet Statement pour obtenir de nouveaux ResultSets. Ceci peut être réalisé en utilisant des blocs try-finally pour garantir que le ResultSet est fermé même si une exception se produit :
// Corrected code: closing the ResultSet objects try { // Execute the first query and obtain ResultSet rs ResultSet rs = statement.executeQuery("SELECT `name` FROM `user` WHERE `id` = " + userId + " LIMIT 1;"); // Use rs to retrieve data if(rs.next()) { String name = rs.getString("name"); } // Close rs rs.close(); // Execute the second query and obtain ResultSet rs2 ResultSet rs2 = statement.executeQuery("SELECT `id` FROM `profiles` WHERE `id` =" + profId + ";"); // Use rs2 to retrieve data while(rs2.next()) { int id = rs2.getInt("id"); int stuff = getStuff(id); pst.setInt(1, stuff); pst.addBatch(); } // Close rs2 rs2.close(); pst.executeBatch(); } catch (Exception e) { e.printStackTrace(); }
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!