Die wichtigsten Softwareversionen, die beim Schreiben dieses Artikels verwendet werden, sind folgende.
Der folgende Code ruft alle EMPNOs aus einer Tabelle namens EMPs ab und gibt sie an die Standardausgabe aus.
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
public class Main {
public static void main(String[] args) {
String url = "jdbc:db2://<hostname>:<port>/<dbname>";
String user = "<user>";
String password = "<password>";
try (Connection con = DriverManager.getConnection(url, user, password)) {
con.setAutoCommit(false);
PreparedStatement ps = con.prepareStatement("SELECT * FROM EMP");
ResultSet rs = ps.executeQuery();
while (rs.next()) {
System.out.println(rs.getString("EMPNO"));
}
} catch (SQLException e) {
e.printStackTrace();
}
}
}
Wenn ich diesen Quellcode kompiliere und ausführe, erhalte ich die folgende Ausnahme, nachdem ich alle EMPNOs in der Standardausgabe gedruckt habe:
com.ibm.db2.jcc.am.SqlException: [jcc][t4][10251][10308][4.26.14]Java, während eine Transaktion für die Verbindung ausgeführt wird.sql.Connection.close()Wurde ersucht.
Die Transaktion bleibt aktiv und die Verbindung kann nicht geschlossen werden. FEHLERCODE=-4471, SQLSTATE=null
at com.ibm.db2.jcc.am.b7.a(b7.java:794)
at com.ibm.db2.jcc.am.b7.a(b7.java:66)
at com.ibm.db2.jcc.am.b7.a(b7.java:133)
at com.ibm.db2.jcc.am.Connection.checkForTransactionInProgress(Connection.java:1484)
at com.ibm.db2.jcc.t4.b.checkForTransactionInProgress(b.java:7581)
at com.ibm.db2.jcc.am.Connection.closeResourcesX(Connection.java:1507)
at com.ibm.db2.jcc.am.Connection.closeX(Connection.java:1493)
at com.ibm.db2.jcc.am.Connection.close(Connection.java:1470)
at Main.main(Main.java:22)
__java.sql.Connection.close ()
kann verstanden werden, weil try-catch-with-resource
es ohne Erlaubnis aufruft, aber zunächst "Die Transaktion bleibt aktiv und die Verbindung kann nicht geschlossen werden." Was für ein Chaos ??? __.
Für Db2 muss die Transaktion mit "COMMIT" oder "ROLLBACK" abgeschlossen werden, bevor die DB-Verbindung geschlossen wird. "COMMIT" und "ROLLBACK" werden nur ausgeführt, wenn Änderungen an den Daten in der Datenbank vorgenommen werden, wie "INSERT" und "DELETE", und "COMMIT" und "ROLLBACK" werden für "SELECT" verwendet, das sich nur auf die Daten bezieht. Ich bin mir sicher, dass es viele Leute gibt, die nicht darauf achten, aber zumindest in Db2 müssen Sie sich der Transaktionen bewusst sein, selbst im Fall von "SELECT".
Im obigen Quellcode wurde Autocommit deaktiviert (con.setAutoCommit (false)
). Wenn auto-commit = true ist, führt der Aufruf von "Connection :: close" dazu, dass der jdbc-Treiber automatisch festgeschrieben wird. Wenn auto-commit = false, wird der Programmierer explizit "Connection :: commit" oder ". Wenn Sie Connection :: rollback` nicht aufrufen, wird die Transaktion nicht abgeschlossen. Mit anderen Worten, im obigen Quellcode haben wir die automatische Festschreibung deaktiviert und versucht, die Verbindung zu schließen, ohne die Transaktion zu bestätigen, was zu "ERRORCODE = -4471" führte.
Connection :: commit
oder Connection :: rollback
auf, um die Transaktion explizit abzuschließenIst das die Gegenmaßnahme (´ ・ ω ・ `)