diff --git a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseProvider.java b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseProvider.java index 8b52e9ef..999db994 100644 --- a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseProvider.java +++ b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseProvider.java @@ -22,10 +22,11 @@ import org.junit.jupiter.api.extension.*; import org.junit.jupiter.api.extension.ExtensionContext.Namespace; +import com.fasterxml.jackson.databind.ObjectMapper; import com.phocassoftware.graphql.database.manager.Database; import com.phocassoftware.graphql.database.manager.VirtualDatabase; import com.phocassoftware.graphql.database.manager.dynamo.DynamoDbManager; -import com.phocassoftware.graphql.database.manager.test.annotations.ProviderFunction; +import com.phocassoftware.graphql.database.manager.test.annotations.*; import com.phocassoftware.graphql.database.manager.test.annotations.TestDatabase; import software.amazon.awssdk.services.dynamodb.DynamoDbAsyncClient; @@ -61,9 +62,9 @@ public boolean supportsParameter(ParameterContext parameterContext, ExtensionCon var testDatabase = getTestDatabase(testMethod); if (testDatabase != null) { - return Stream - .of(testDatabase.providers()) - .map(t -> create(t)) + return testDatabase + .providers() + .stream() .anyMatch(provider -> parameterContext.getParameter().getType().isAssignableFrom(provider.type())); } @@ -89,11 +90,14 @@ public Object resolveParameter(ParameterContext parameterContext, ExtensionConte public void beforeEach(ExtensionContext extensionContext) throws Exception { var wrapper = getServer(); final var testMethod = extensionContext.getRequiredTestMethod(); + + TestDatabaseSetup setup; + var testDatabase = getTestDatabase(testMethod); var classPath = testDatabase.classPath(); var hashed = testDatabase.hashed(); - var objectMapper = testDatabase.objectMapper().getConstructor().newInstance().get(); + var objectMapper = testDatabase.objectMapper(); final var withHistory = Arrays .stream(testMethod.getParameters()) @@ -126,9 +130,9 @@ public void beforeEach(ExtensionContext extensionContext) throws Exception { } else if (type.isAssignableFrom(Database.class)) { return provider.getDatabase(); } else { - var builder = Stream - .of(testDatabase.providers()) - .map(t -> create(t)) + var builder = testDatabase + .providers() + .stream() .filter(p -> type.isAssignableFrom(p.type())) .findAny() .orElse(null); @@ -180,19 +184,37 @@ private ServerWrapper getServer() throws Exception { } - private TestDatabase getTestDatabase(AnnotatedElement annotatedElement) { - var annotation = annotatedElement.getAnnotation(TestDatabase.class); - if (annotation != null) { - return annotation; - } - for (var a : annotatedElement.getAnnotations()) { - annotation = getTestDatabase(a.annotationType()); + private TestDatabaseSetup getTestDatabase(AnnotatedElement annotatedElement) { + try { + var annotation = annotatedElement.getAnnotation(TestDatabase.class); + var classBased = annotatedElement.getAnnotation(TestDatabaseBuilder.class); + if (annotation == null && classBased == null) { + for (var a : annotatedElement.getAnnotations()) { + var setup = getTestDatabase(a.annotationType()); + if (setup != null) { + return setup; + } + } + } if (annotation != null) { - return annotation; + var providers = Stream + .of(annotation.providers()) + .map(t -> create(t)) + .toList(); + + var objectMapper = annotation.objectMapper().getConstructor().newInstance().get(); + return new TestDatabaseAnnotationSetup(annotation.classPath(), annotation.hashed(), objectMapper, providers); } + + return classBased.value().getConstructor().newInstance(); + + } catch (ReflectiveOperationException e) { + throw new RuntimeException(e); } - return null; } record ServerWrapper(DynamoDbClient client, DynamoDbAsyncClient clientAsync, DynamoDbStreamsAsyncClient streamClient) {} + + record TestDatabaseAnnotationSetup(String classPath, boolean hashed, ObjectMapper objectMapper, List> providers) implements + TestDatabaseSetup {} } diff --git a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabase.java b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabase.java index e1148564..5d9f0647 100644 --- a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabase.java +++ b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabase.java @@ -33,4 +33,5 @@ Class> objectMapper(); Class>[] providers() default {}; + } diff --git a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseBuilder.java b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseBuilder.java new file mode 100644 index 00000000..6358ad60 --- /dev/null +++ b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseBuilder.java @@ -0,0 +1,30 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the License + * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express + * or implied. See the License for the specific language governing permissions and limitations under + * the License. + */ + +package com.phocassoftware.graphql.database.manager.test.annotations; + +import java.lang.annotation.*; +import java.util.function.Supplier; + +import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.phocassoftware.graphql.database.manager.test.TestDatabaseProvider; + +@Target(ElementType.ANNOTATION_TYPE) +@Retention(RetentionPolicy.RUNTIME) +@Test +@ExtendWith(TestDatabaseProvider.class) +public @interface TestDatabaseBuilder { + Class value(); +} diff --git a/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseSetup.java b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseSetup.java new file mode 100644 index 00000000..13105390 --- /dev/null +++ b/graphql-database-manager-test/src/main/java/com/phocassoftware/graphql/database/manager/test/annotations/TestDatabaseSetup.java @@ -0,0 +1,30 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the License + * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express + * or implied. See the License for the specific language governing permissions and limitations under + * the License. + */ +package com.phocassoftware.graphql.database.manager.test.annotations; + +import java.util.List; + +import com.fasterxml.jackson.databind.ObjectMapper; + +public interface TestDatabaseSetup { + + default List> providers() { + return List.of(); + } + + String classPath(); + + boolean hashed(); + + ObjectMapper objectMapper(); + +} diff --git a/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/DynamoDbQueryTest.java b/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/DynamoDbQueryTest.java index dc444591..bcf868e6 100644 --- a/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/DynamoDbQueryTest.java +++ b/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/DynamoDbQueryTest.java @@ -22,7 +22,7 @@ final class DynamoDbQueryTest { - @TestDatabase + @TestDatabaseClassBased void testSimpleQuery(final Database db) throws InterruptedException, ExecutionException { db.put(new SimpleTable("garry")).get(); db.put(new SimpleTable("bob")).get(); diff --git a/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseClassBased.java b/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseClassBased.java new file mode 100644 index 00000000..1fd93396 --- /dev/null +++ b/graphql-database-manager-test/src/test/java/com/phocassoftware/graphql/database/manager/test/TestDatabaseClassBased.java @@ -0,0 +1,43 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the License + * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express + * or implied. See the License for the specific language governing permissions and limitations under + * the License. + */ +package com.phocassoftware.graphql.database.manager.test; + +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.phocassoftware.graphql.database.manager.test.annotations.TestDatabaseSetup; + +@Retention(RetentionPolicy.RUNTIME) +@com.phocassoftware.graphql.database.manager.test.annotations.TestDatabaseBuilder(value = TestDatabaseClassBased.ClassBaseSetup.class) +public @interface TestDatabaseClassBased { + + class ClassBaseSetup implements TestDatabaseSetup { + + @Override + public String classPath() { + return "com.phocassoftware.graphql.database.manager.test"; + } + + @Override + public boolean hashed() { + return true; + } + + @Override + public ObjectMapper objectMapper() { + return new ObjectMapperCreator().get(); + } + + } + +}