diff --git a/blackbox-test-inject/src/main/java/io/ebean/Database.java b/blackbox-test-inject/src/main/java/io/ebean/Database.java new file mode 100644 index 000000000..47416c4f3 --- /dev/null +++ b/blackbox-test-inject/src/main/java/io/ebean/Database.java @@ -0,0 +1,15 @@ +package io.ebean; + +/** + * Simulate the Ebean io.ebean.Database interface with a shutdown() method. + *
+ * For "Graceful Shutdown" we desire this to be shutdown last.
+ */
+public interface Database {
+
+ /** Shutdown including underlying DataSources. We want this to occur LAST. */
+ void shutdown();
+
+ /** Test only method */
+ boolean isShutdown();
+}
diff --git a/blackbox-test-inject/src/main/java/io/ebean/MyDatabase.java b/blackbox-test-inject/src/main/java/io/ebean/MyDatabase.java
new file mode 100644
index 000000000..6d4c10310
--- /dev/null
+++ b/blackbox-test-inject/src/main/java/io/ebean/MyDatabase.java
@@ -0,0 +1,16 @@
+package io.ebean;
+
+public class MyDatabase implements Database {
+
+ public boolean shutdownCalled = false;
+
+ @Override
+ public void shutdown() {
+ shutdownCalled = true;
+ }
+
+ @Override
+ public boolean isShutdown() {
+ return shutdownCalled;
+ }
+}
diff --git a/blackbox-test-inject/src/main/java/org/example/myapp/config/AppConfig.java b/blackbox-test-inject/src/main/java/org/example/myapp/config/AppConfig.java
index 57631e304..b8cd7cbfe 100644
--- a/blackbox-test-inject/src/main/java/org/example/myapp/config/AppConfig.java
+++ b/blackbox-test-inject/src/main/java/org/example/myapp/config/AppConfig.java
@@ -1,6 +1,8 @@
package org.example.myapp.config;
import io.avaje.inject.*;
+import io.ebean.Database;
+import io.ebean.MyDatabase;
import jakarta.inject.Inject;
import jakarta.inject.Named;
import org.example.myapp.HelloData;
@@ -14,6 +16,12 @@ public class AppConfig {
public static AtomicBoolean BEAN_AUTO_CLOSED = new AtomicBoolean();
+ /** Because this is a io.ebean.Database, we know it should be shutdown() last */
+ @Bean // Effectively default to @Bean(destroyMethod = "shutdown", destroyPriority = Integer.MAX_VALUE)
+ Database database() {
+ return new MyDatabase();
+ }
+
@PreDestroy(priority = 999)
void close() {
MyDestroyOrder.add("AppConfig");
diff --git a/blackbox-test-inject/src/test/java/org/example/myapp/DefaultDestroyTest.java b/blackbox-test-inject/src/test/java/org/example/myapp/DefaultDestroyTest.java
new file mode 100644
index 000000000..9e3168662
--- /dev/null
+++ b/blackbox-test-inject/src/test/java/org/example/myapp/DefaultDestroyTest.java
@@ -0,0 +1,22 @@
+package org.example.myapp;
+
+import io.avaje.inject.BeanScope;
+import io.ebean.Database;
+import org.junit.jupiter.api.Test;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+class DefaultDestroyTest {
+
+ @Test
+ void expect_ebeanDatabase_hasShutdownByDefault() {
+ try (BeanScope beanScope = BeanScope.builder().build()) {
+ Database database = beanScope.get(Database.class);
+
+ assertThat(database.isShutdown()).isFalse();
+ beanScope.close();
+
+ assertThat(database.isShutdown()).isTrue();
+ }
+ }
+}
diff --git a/inject-generator/src/main/java/io/avaje/inject/generator/MethodReader.java b/inject-generator/src/main/java/io/avaje/inject/generator/MethodReader.java
index cc4119270..dfc31234e 100644
--- a/inject-generator/src/main/java/io/avaje/inject/generator/MethodReader.java
+++ b/inject-generator/src/main/java/io/avaje/inject/generator/MethodReader.java
@@ -3,10 +3,7 @@
import javax.lang.model.element.*;
import javax.lang.model.type.TypeKind;
import javax.lang.model.type.TypeMirror;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
import static io.avaje.inject.generator.Constants.CONDITIONAL_DEPENDENCY;
import static io.avaje.inject.generator.ProcessingContext.asElement;
@@ -15,6 +12,13 @@ final class MethodReader {
private static final String CODE_COMMENT_BUILD_FACTORYBEAN = " /**\n * Create and register %s via factory bean method %s#%s().\n */";
+ private static final Map