Fix for #3012 Manual server shutdown leads to memory leak

The issue being that shutdown() // with no args was
not calling ShutdownManager.unregisterDatabase(this)
noting that shutdown(boolean, boolean) did.

This change merges the old shutdownInternal(boolean, boolean)
method into shutdown(boolean, boolean) and simplifies
shutdown() to just call shutdown(boolean, boolean).
This commit is contained in:
Rob Bygrave
2023-03-29 20:59:23 +13:00
parent b4f309c219
commit e1522df8a5
3 changed files with 20 additions and 35 deletions
@@ -143,7 +143,7 @@ public final class ShutdownManager {
}
// shutdown any registered servers that have not
// already been shutdown manually
for (Database server : databases) {
for (Database server : new ArrayList<>(databases)) {
try {
server.shutdown();
} catch (Exception ex) {
@@ -354,50 +354,35 @@ public final class DefaultServer implements SpiServer, SpiEbeanServer {
@Override
public void shutdown() {
lock.lock();
try {
shutdownInternal(true, false);
} finally {
lock.unlock();
}
shutdown(true, false);
}
/**
* Shutting down manually.
*/
@Override
public void shutdown(boolean shutdownDataSource, boolean deregisterDriver) {
lock.lock();
try {
ShutdownManager.unregisterDatabase(this);
shutdownInternal(shutdownDataSource, deregisterDriver);
log.log(TRACE, "shutting down instance {0}", serverName);
if (shutdown) {
// already shutdown
return;
}
shutdownPlugins();
autoTuneService.shutdown();
// shutdown background threads
backgroundExecutor.shutdown();
// shutdown DataSource (if its an Ebean one)
transactionManager.shutdown(shutdownDataSource, deregisterDriver);
dumpMetrics();
shutdown = true;
if (shutdownDataSource) {
config.setDataSource(null);
}
} finally {
lock.unlock();
}
}
/**
* Shutdown the services like threads and DataSource.
*/
private void shutdownInternal(boolean shutdownDataSource, boolean deregisterDriver) {
log.log(TRACE, "shutting down instance {0}", serverName);
if (shutdown) {
// already shutdown
return;
}
shutdownPlugins();
autoTuneService.shutdown();
// shutdown background threads
backgroundExecutor.shutdown();
// shutdown DataSource (if its an Ebean one)
transactionManager.shutdown(shutdownDataSource, deregisterDriver);
dumpMetrics();
shutdown = true;
if (shutdownDataSource) {
config.setDataSource(null);
}
}
private void dumpMetrics() {
if (config.isDumpMetricsOnShutdown()) {
new DumpMetrics(this, config.getDumpMetricsOptions()).dump();
@@ -1,13 +1,13 @@
package io.ebeaninternal.dbmigration.model.build;
import io.localtest.BaseTestCase;
import io.ebean.DatabaseFactory;
import io.ebean.config.DatabaseConfig;
import io.ebeaninternal.api.SpiEbeanServer;
import io.ebeaninternal.dbmigration.ddlgeneration.DdlOptions;
import io.ebeaninternal.dbmigration.ddlgeneration.Helper;
import io.ebeaninternal.dbmigration.model.CurrentModel;
import io.localtest.BaseTestCase;
import org.junit.jupiter.api.Test;
import org.tests.model.basic.Person;
import org.tests.model.basic.Phone;
@@ -66,7 +66,7 @@ class ModelBuild_explicitSequencesTest extends BaseTestCase {
.startsWith("-- Generated by ebean")
.endsWith(Helper.asText(this, "/assert/ModelBuild_explicitSequencesTest/pg-apply.sql"));
} finally {
ebeanServer.shutdown();
ebeanServer.shutdown(true, false);
}
}