Obwohl Tomcat die Deregistrierung des JDBC-Treibers für Sie erzwingt, ist es dennoch eine gute Praxis, alle von Ihrer Webapplikation erstellten Ressourcen bei der Kontextzerstörung zu bereinigen, für den Fall, dass Sie zu einem anderen Servlet-Container wechseln, der nicht die Prüfungen zur Vermeidung von Speicherlecks durchführt, die Tomcat durchführt.
Die Methode der pauschalen Abmeldung von Fahrern ist jedoch gefährlich. Einige Fahrer, die von der DriverManager.getDrivers()
Methode kann vom übergeordneten ClassLoader (d.h. dem Classloader des Servlet-Containers) und nicht vom ClassLoader des Webapp-Kontextes geladen worden sein (z.B. kann es sein, dass sie sich im lib-Ordner des Containers und nicht im lib-Ordner der Webapp befinden und daher im gesamten Container gemeinsam genutzt werden). Eine Deregistrierung wirkt sich auf alle anderen Webapps aus, die sie möglicherweise verwenden (oder sogar auf den Container selbst).
Daher sollte man überprüfen, ob der ClassLoader für jeden Treiber der ClassLoader der Webapp ist, bevor man ihn deregistriert. Also, in der Methode contextDestroyed() Ihres ContextListeners:
public final void contextDestroyed(ServletContextEvent sce) {
// ... First close any background tasks which may be using the DB ...
// ... Then close any DB connection pools ...
// Now deregister JDBC drivers in this context's ClassLoader:
// Get the webapp's ClassLoader
ClassLoader cl = Thread.currentThread().getContextClassLoader();
// Loop through all drivers
Enumeration<Driver> drivers = DriverManager.getDrivers();
while (drivers.hasMoreElements()) {
Driver driver = drivers.nextElement();
if (driver.getClass().getClassLoader() == cl) {
// This driver was registered by the webapp's ClassLoader, so deregister it:
try {
log.info("Deregistering JDBC driver {}", driver);
DriverManager.deregisterDriver(driver);
} catch (SQLException ex) {
log.error("Error deregistering JDBC driver {}", driver, ex);
}
} else {
// driver was not registered by the webapp's ClassLoader and may be in use elsewhere
log.trace("Not deregistering JDBC driver {} as it does not belong to this webapp's ClassLoader", driver);
}
}
}