it-swarm.com.de

JDBC-Verbindungen im Pool schließen

Unser Standardcodeabschnitt für die Verwendung von JDBC ist ...

Connection conn = getConnection(...);
Statement  stmt = conn.conn.createStatement (ResultSet.TYPE_SCROLL_INSENSITIVE,
                                                ResultSet.CONCUR_READ_ONLY);
ResultSet  rset = stmt.executeQuery (sqlQuery);

// do stuff with rset

rset.close(); stmt.close(); conn.close();

Frage 1: Wenn Sie Connection Pool verwenden, sollte die Verbindung am Ende geschlossen werden? Wenn ja, geht der Zweck des Poolings nicht verloren? Und wenn nicht, woher weiß die DataSource, wann eine bestimmte Instanz von Connection freigegeben wird und wiederverwendet werden kann? Ich bin ein wenig verwirrt über dieses, alle Hinweise schätzten es.

Frage 2: Stimmt die folgende Methode dem Standard nahe? Sieht wie ein Versuch aus, eine Verbindung aus dem Pool zu erhalten, und wenn DataSource nicht eingerichtet werden kann, verwenden Sie den altmodischen DriverManager. Wir sind nicht einmal sicher, welcher Teil zur Laufzeit ausgeführt wird . Sollte man die obige Frage wiederholen, sollte man die Verbindung schließen, die aus einer solchen Methode kommt?

Danke, MS.

synchronized public Connection getConnection (boolean pooledConnection)
                                                        throws SQLException {
        if (pooledConnection) {
                if (ds == null) {
                        try {
                                Context envCtx = (Context)
                                        new InitialContext().lookup("Java:comp/env");
                                ds = (DataSource) envCtx.lookup("jdbc/NamedInTomcat");
                                return ds.getConnection();
                        } catch (NamingException e) {
                                e.printStackTrace();
                }}
                return (ds == null) ? getConnection (false) : ds.getConnection();
        }
        return DriverManager.getConnection(
                "jdbc:mysql://"+ipaddy+":"+dbPort +"/" + dbName, uName, pWord);
}

Edit: Ich denke, wir bekommen die gepoolte Verbindung, da wir keine Stack-Trace sehen.

97

Wenn man Connection Pool verwendet, sollte man am Ende die Verbindung schließen? Wenn ja, geht der Zweck des Poolings nicht verloren? Und wenn nicht, woher weiß die DataSource, wann eine bestimmte Instanz von Connection freigegeben wird und wiederverwendet werden kann? Ich bin ein wenig verwirrt über dieses, alle Hinweise schätzten es.

Ja, natürlich müssen Sie auch die gepoolte Verbindung schließen. Es ist eigentlich ein Wrapper um die eigentliche Verbindung. Es wird unter den Abdeckungen die eigentliche Verbindung zum Pool freigeben. Es ist weiter Sache des Pools, zu entscheiden, ob die tatsächliche Verbindung tatsächlich geschlossen oder für einen neuen getConnection()-Aufruf wiederverwendet wird. Unabhängig davon, ob Sie einen Verbindungspool verwenden oder nicht, sollten Sie always alle JDBC-Ressourcen in umgekehrter Reihenfolge im finally-Block des try-Blocks schließen, wo Sie sie erworben haben. In Java 7 kann dies mit der Anweisung try-with-resources weiter vereinfacht werden.


Ist die folgende Methode etwas vom Standard? Sieht wie ein Versuch aus, eine Verbindung aus dem Pool zu erhalten, und wenn DataSource nicht eingerichtet werden kann, verwenden Sie den altmodischen DriverManager. Wir sind nicht einmal sicher, welcher Teil zur Laufzeit ausgeführt wird. Wenn Sie die obige Frage wiederholen, sollte die Verbindung geschlossen werden, die von einer solchen Methode ausgeht?

Das Beispiel ist ziemlich gruselig. Sie müssen die Variable DataSource nur einmal während des Starts der Anwendung in einem Konstruktor/einer Initialisierung einer anwendungsweiten DB-Konfigurationsklasse nachschlagen/initialisieren. Rufen Sie dann einfach getConnection() für die gleiche Datenquelle während der restlichen Lebensdauer der Anwendung auf. Keine Synchronisation oder Nullchecks erforderlich.

Siehe auch:

108
BalusC

Die Pools geben normalerweise ein umschlossenes Connection-Objekt zurück, bei dem die close () -Methode überschrieben wird. Dabei wird normalerweise die Verbindung zum Pool zurückgegeben. Das Aufrufen von close () ist in Ordnung und wahrscheinlich noch erforderlich.

Eine close () -Methode würde wahrscheinlich so aussehen:

public void close() throws SQLException {
  pool.returnConnection(this);
}

Für Ihre zweite Frage könnten Sie einen Logger hinzufügen, um anzuzeigen, ob der unterste Block jemals ausgeführt wird. Ich würde mir vorstellen, dass Sie nur die eine oder andere Möglichkeit für die Konfiguration Ihrer Datenbankverbindungen haben möchten. Wir verwenden ausschließlich einen Pool für unsere Datenbankzugriffe. In jedem Fall wäre das Schließen der Verbindung sehr wichtig, um Lecks zu vermeiden.

21
taer

Tatsächlich besteht der beste Ansatz für das Verbindungsmanagement darin, sie an keinen Code zu binden. 

Erstellen Sie eine SQLExecutor-Klasse, die der einzige Ort ist, an dem Verbindungen geöffnet und geschlossen werden. 

Der gesamte Rest der Anwendung pumpt dann Anweisungen in den Executor, anstatt Verbindungen aus dem Pool zu erhalten und sie überall zu verwalten (oder zu verwalten).

Sie können beliebig viele Instanzen des Executors haben, aber Sie sollten keinen Code schreiben, der in seinem eigenen Namen Verbindungen öffnet und schließt.

Praktischerweise können Sie damit auch Ihre gesamte SQL mit einem einzigen Satz von Code protokollieren.

0