diff --git a/pom.xml b/pom.xml
index 88855f149..5e209f7f7 100644
--- a/pom.xml
+++ b/pom.xml
@@ -48,6 +48,7 @@
1.14.0
3.22.0
4.2.0
+ 4.8.141
3.12.0
2.11.0
0.6.0
@@ -278,13 +279,18 @@
${dependency.testcontainers.version}
+
+ io.github.classgraph
+ classgraph
+ ${dependency.classgraph.version}
+
+
+
com.google.guava
guava
${dependency.guava.version}
-
-
com.google.protobuf
protobuf-java
diff --git a/qa/pom.xml b/qa/pom.xml
index ccf5995c6..6788213b0 100644
--- a/qa/pom.xml
+++ b/qa/pom.xml
@@ -90,8 +90,14 @@
- com.google.guava
- guava
+ io.github.classgraph
+ classgraph
+ test
+
+
+
+ org.junit.jupiter
+ junit-jupiter-params
test
diff --git a/qa/src/test/java/io/camunda/zeebe/process/test/qa/ExtendAbstractsTest.java b/qa/src/test/java/io/camunda/zeebe/process/test/qa/ExtendAbstractsTest.java
index 8d4dba3fd..f51aeedc9 100644
--- a/qa/src/test/java/io/camunda/zeebe/process/test/qa/ExtendAbstractsTest.java
+++ b/qa/src/test/java/io/camunda/zeebe/process/test/qa/ExtendAbstractsTest.java
@@ -15,80 +15,76 @@
*/
package io.camunda.zeebe.process.test.qa;
-import com.google.common.reflect.ClassPath;
import io.camunda.zeebe.process.test.extension.ZeebeProcessTest;
-import java.io.IOException;
-import java.lang.annotation.Annotation;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Optional;
+import io.github.classgraph.ClassGraph;
+import io.github.classgraph.ClassInfo;
+import io.github.classgraph.ClassInfoList;
+import java.util.stream.Stream;
import org.assertj.core.api.SoftAssertions;
-import org.junit.jupiter.api.Test;
+import org.junit.jupiter.params.ParameterizedTest;
+import org.junit.jupiter.params.provider.Arguments;
+import org.junit.jupiter.params.provider.MethodSource;
class ExtendAbstractsTest {
- public static final String EMBEDDED = "embedded";
- public static final String TESTCONTAINER = "testcontainer";
public static final Class EMBEDDED_ANNOTATION = ZeebeProcessTest.class;
public static final Class
TESTCONTAINER_ANNOTATION =
io.camunda.zeebe.process.test.extension.testcontainer.ZeebeProcessTest.class;
- private static final String BASE_PACKAGE = "io.camunda.zeebe.process.test.qa";
- private static final String ABSTRACTS = "abstracts";
+ private static final String ABSTRACT_PACKAGE = "io.camunda.zeebe.process.test.qa.abstracts";
+ private static final String EMBEDDED_PACKAGE = "io.camunda.zeebe.process.test.qa.embedded";
+ private static final String TESTCONTAINER_PACKAGE =
+ "io.camunda.zeebe.process.test.qa.testcontainer";
- @Test
- void testAbstractClassesAreExtendedWithBothExtensions() throws IOException {
- final Map>> classes = new HashMap<>();
- classes.put(ABSTRACTS, new ArrayList<>());
- classes.put(EMBEDDED, new ArrayList<>());
- classes.put(TESTCONTAINER, new ArrayList<>());
+ private static final ClassInfoList EXTENDING_CLASSES =
+ new ClassGraph()
+ .acceptPackages(EMBEDDED_PACKAGE, TESTCONTAINER_PACKAGE)
+ .ignoreClassVisibility()
+ .enableAnnotationInfo()
+ .scan()
+ .getAllStandardClasses()
+ .filter(info -> !info.isInnerClass());
- ClassPath.from(ClassLoader.getSystemClassLoader()).getTopLevelClasses().stream()
- .filter(clazz -> clazz.getPackageName().startsWith(BASE_PACKAGE))
- .forEach(
- classInfo -> {
- if (classInfo.getPackageName().contains(BASE_PACKAGE + "." + ABSTRACTS)) {
- classes.get(ABSTRACTS).add(classInfo.load());
- } else if (classInfo.getPackageName().contains(BASE_PACKAGE + "." + EMBEDDED)) {
- classes.get(EMBEDDED).add(classInfo.load());
- } else if (classInfo.getPackageName().contains(BASE_PACKAGE + "." + TESTCONTAINER)) {
- classes.get(TESTCONTAINER).add(classInfo.load());
- }
- });
+ @ParameterizedTest(name = "{0}")
+ @MethodSource("provideAbstractClasses")
+ void testAbstractClassIsExtendedWithBothExtensions(
+ final String className, final Class> abstractClass) {
+ final ClassInfoList embeddedClass =
+ EXTENDING_CLASSES
+ .filter(info -> info.getPackageName().contains("embedded"))
+ .filter(info -> info.extendsSuperclass(abstractClass))
+ .filter(info -> info.hasAnnotation(EMBEDDED_ANNOTATION));
+
+ final ClassInfoList testcontainerClass =
+ EXTENDING_CLASSES
+ .filter(info -> info.getPackageName().contains("testcontainer"))
+ .filter(info -> info.extendsSuperclass(abstractClass))
+ .filter(info -> info.hasAnnotation(TESTCONTAINER_ANNOTATION));
final SoftAssertions softly = new SoftAssertions();
- classes
- .get(ABSTRACTS)
- .forEach(
- abstractClass -> {
- assertExtendingClass(
- abstractClass, classes.get(EMBEDDED), EMBEDDED, EMBEDDED_ANNOTATION, softly);
- assertExtendingClass(
- abstractClass,
- classes.get(TESTCONTAINER),
- TESTCONTAINER,
- TESTCONTAINER_ANNOTATION,
- softly);
- });
+ softly
+ .assertThat(embeddedClass)
+ .withFailMessage(
+ "Expected 1 embedded implementation of %s, but found %d: %s",
+ className, embeddedClass.size(), embeddedClass)
+ .hasSize(1);
+ softly
+ .assertThat(testcontainerClass)
+ .withFailMessage(
+ "Expected 1 testcontainer implementation of %s, but found %d: %s",
+ className, embeddedClass.size(), embeddedClass)
+ .hasSize(1);
softly.assertAll();
}
- private void assertExtendingClass(
- final Class> abstractClass,
- final List> classes,
- final String classPackage,
- final Class extends Annotation> annotation,
- final SoftAssertions softly) {
- final Optional> clazzOptional =
- classes.stream().filter(abstractClass::isAssignableFrom).findFirst();
- softly
- .assertThat(clazzOptional)
- .withFailMessage(
- "Package %s.%s does not contain a class extending %s",
- BASE_PACKAGE, classPackage, abstractClass)
- .isNotEmpty();
- clazzOptional.ifPresent(clazz -> softly.assertThat(clazz).hasAnnotation(annotation));
+ private static Stream provideAbstractClasses() {
+ return new ClassGraph()
+ .acceptPackages(ABSTRACT_PACKAGE)
+ .scan()
+ .getAllStandardClasses()
+ .filter(ClassInfo::isAbstract)
+ .filter(info -> !info.isInnerClass())
+ .stream()
+ .map(info -> Arguments.of(info.getSimpleName(), info.loadClass()));
}
}