diff --git a/core/src/test/java/dev/morphia/test/TemplatedTestBase.java b/core/src/test/java/dev/morphia/test/TemplatedTestBase.java index e740ebe16ae..d26758c888a 100644 --- a/core/src/test/java/dev/morphia/test/TemplatedTestBase.java +++ b/core/src/test/java/dev/morphia/test/TemplatedTestBase.java @@ -9,11 +9,13 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.List; +import java.util.Objects; import java.util.regex.Pattern; import com.fasterxml.jackson.databind.ObjectMapper; import com.mongodb.client.MongoCollection; import com.mongodb.lang.NonNull; +import com.mongodb.lang.Nullable; import dev.morphia.aggregation.Aggregation; import dev.morphia.aggregation.AggregationImpl; @@ -133,9 +135,9 @@ protected static String toString(List actual, String prefix) { @Deprecated public void testQuery(MorphiaQuery query, FindOptions options, boolean orderMatters) { - var resourceName = discoverResourceName(new Exception().getStackTrace()); + var resourceName = discoverResourceName(); - loadData(getDs().getCollection(query.getEntityClass()).getNamespace().getCollectionName()); + loadData(resourceName, getDs().getCollection(query.getEntityClass()).getNamespace().getCollectionName()); List actual = runQuery(resourceName, query, options); @@ -148,22 +150,26 @@ public void testQuery(MorphiaQuery query, FindOptions options, boolean or } } - protected void loadData(String collection) { + protected void loadData(String resourceName, String collection) { if (!skipDataCheck) { - var resourceName = discoverResourceName(new Exception().getStackTrace()); insert(collection, loadJson(format("%s/%s/data.json", prefix(), resourceName), "data", true)); } } protected void loadData(String collection, int index) { if (!skipDataCheck) { - var resourceName = discoverResourceName(new Exception().getStackTrace()); + insert(collection, loadJson(format("%s/%s/data%d.json", prefix(), discoverResourceName(), index), "data", true)); + } + } + + protected void loadData(String resourceName, String collection, int index) { + if (!skipDataCheck) { insert(collection, loadJson(format("%s/%s/data%d.json", prefix(), resourceName, index), "data", true)); } } - protected void loadIndex(String collectionName) { - var resourceName = discoverResourceName(new Exception().getStackTrace()); + protected void loadIndex(String resourceName, String collectionName) { + final StackTraceElement[] stackTrace = new Exception().getStackTrace(); MongoCollection collection = getDatabase().getCollection(collectionName); List documents = loadJson("%s/%s/index.json".formatted(prefix(), resourceName), "index", false); documents.forEach(document -> { @@ -266,6 +272,21 @@ protected Document loadQuery(String pipelineName) { return parseAction(stream).get(0); } + protected String loadTestName(String resourceName) { + String name = format("%s/%s/name", prefix(), resourceName); + + InputStream stream = getClass().getResourceAsStream(name); + if (stream == null) { + fail(format("missing name file: %s", name)); + } + + try (var reader = new BufferedReader(new InputStreamReader(stream))) { + return reader.readLine(); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + private List loadPipeline(String pipelineName) { InputStream stream = getClass().getResourceAsStream(pipelineName); if (stream == null) { @@ -377,11 +398,10 @@ protected List runQuery(@NonNull String queryTemplate, @NonNull MorphiaQu } } - protected String discoverResourceName(StackTraceElement[] stackTrace) { - String methodName = Arrays.stream(stackTrace) - .filter(e -> isTestMethod(e)) - .findFirst() - .get().getMethodName(); + protected String discoverResourceName() { + var method = findTestMethod(); + String methodName = method.getName(); + if (methodName.startsWith("test")) { methodName = methodName.substring(4); methodName = methodName.substring(0, 1).toLowerCase() + methodName.substring(1); @@ -389,14 +409,23 @@ protected String discoverResourceName(StackTraceElement[] stackTrace) { return methodName; } - private boolean isTestMethod(StackTraceElement element) { + protected Method findTestMethod() { + return stream(new Exception().getStackTrace()) + .map(this::isTestMethod) + .filter(Objects::nonNull) + .findFirst() + .get(); + } + + @Nullable + private Method isTestMethod(StackTraceElement element) { try { Class klass = Class.forName(element.getClassName()); Method method = klass.getDeclaredMethod(element.getMethodName()); - return method.getAnnotation(Test.class) != null; + return method.getAnnotation(Test.class) != null ? method : null; } catch (ReflectiveOperationException e) { - return false; + return null; } } diff --git a/core/src/test/java/dev/morphia/test/aggregation/AggregationTest.java b/core/src/test/java/dev/morphia/test/aggregation/AggregationTest.java index ce08cc17856..e9656340bee 100644 --- a/core/src/test/java/dev/morphia/test/aggregation/AggregationTest.java +++ b/core/src/test/java/dev/morphia/test/aggregation/AggregationTest.java @@ -48,9 +48,9 @@ public void testPipeline(ServerVersion serverVersion, Function, Aggregation> pipeline) { checkMinServerVersion(serverVersion); checkMinDriverVersion(minDriver); - var resourceName = discoverResourceName(new Exception().getStackTrace()); - loadData(AGG_TEST_COLLECTION); - loadIndex(AGG_TEST_COLLECTION); + var resourceName = discoverResourceName(); + loadData(resourceName, AGG_TEST_COLLECTION); + loadIndex(resourceName, AGG_TEST_COLLECTION); List actual = runPipeline(resourceName, pipeline.apply(getDs().aggregate(AGG_TEST_COLLECTION))); diff --git a/core/src/test/java/dev/morphia/test/query/filters/FilterTest.java b/core/src/test/java/dev/morphia/test/query/filters/FilterTest.java index e73fe9f0657..5a0ab1cf6a8 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/FilterTest.java +++ b/core/src/test/java/dev/morphia/test/query/filters/FilterTest.java @@ -1,5 +1,6 @@ package dev.morphia.test.query.filters; +import java.lang.reflect.Method; import java.util.List; import java.util.function.Function; @@ -12,12 +13,17 @@ import dev.morphia.test.util.Comparanator; import org.bson.Document; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.testng.annotations.Test; import static java.lang.String.format; import static java.util.Collections.emptyList; import static org.testng.Assert.assertEquals; public class FilterTest extends TemplatedTestBase { + private static final Logger LOG = LoggerFactory.getLogger(FilterTest.class); + public FilterTest() { super(buildConfig(Martian.class, User.class) .applyIndexes(true) @@ -33,11 +39,13 @@ public void testQuery(ServerVersion serverVersion, boolean removeIds, boolean orderMatters, Function, Query> function) { + checkMinServerVersion(serverVersion); checkMinDriverVersion(minDriver); - var resourceName = discoverResourceName(new Exception().getStackTrace()); - loadData(AGG_TEST_COLLECTION); - loadIndex(AGG_TEST_COLLECTION); + var resourceName = discoverResourceName(); + validateTestName(resourceName); + loadData(resourceName, AGG_TEST_COLLECTION); + loadIndex(resourceName, AGG_TEST_COLLECTION); List actual = runQuery(resourceName, function.apply(getDs().find(AGG_TEST_COLLECTION, Document.class) .disableValidation())); @@ -57,13 +65,22 @@ public void testQuery(ServerVersion serverVersion, } } + private void validateTestName(String resourceName) { + Method method = findTestMethod(); + Test test = method.getAnnotation(Test.class); + assertEquals( + loadTestName(resourceName), test.testName(), + "%s#%s does not have a name configured on the test.".formatted(method.getDeclaringClass().getName(), + method.getName())); + } + @SuppressWarnings({ "unchecked", "rawtypes" }) protected List runQuery(String pipelineTemplate, Query query) { - String pipelineName = format("%s/%s/action.json", prefix(), pipelineTemplate); + String resourceName = format("%s/%s/action.json", prefix(), pipelineTemplate); Document document = ((MorphiaQuery) query).toDocument(); if (!skipActionCheck) { - Document target = loadQuery(pipelineName); + Document target = loadQuery(resourceName); assertEquals(toJson(document), toJson(target), "Should generate the same query document"); } diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestAll.java b/core/src/test/java/dev/morphia/test/query/filters/TestAll.java index 1f77189d7e6..2f449bb8dc7 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestAll.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestAll.java @@ -12,12 +12,12 @@ import static dev.morphia.query.filters.Filters.gt; public class TestAll extends FilterTest { - @Test + @Test(testName = "Use ``$all`` to Match Values") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter(all("tags", List.of("appliance", "school", "book")))); } - @Test + @Test(testName = "Use ``$all`` with ``$elemMatch``") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter(all("qty", List.of(elemMatch(eq("size", "M"), gt("num", 50)), diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllClear.java b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllClear.java index c40a2c92f1b..6e3e9080a7f 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllClear.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllClear.java @@ -7,19 +7,19 @@ import static dev.morphia.query.filters.Filters.bitsAllClear; public class TestBitsAllClear extends FilterTest { - @Test + @Test(testName = "Bit Position Array") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllClear("a", new int[] { 1, 5 }))); } - @Test + @Test(testName = "Integer Bitmask") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllClear("a", 35))); } - @Test + @Test(testName = "BinData Bitmask") public void testExample3() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllClear("a", new byte[] { 32 }))); diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllSet.java b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllSet.java index de6067e76f6..43b93c3e3cf 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllSet.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAllSet.java @@ -7,19 +7,19 @@ import static dev.morphia.query.filters.Filters.bitsAllSet; public class TestBitsAllSet extends FilterTest { - @Test + @Test(testName = "Bit Position Array") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllSet("a", new int[] { 1, 5 }))); } - @Test + @Test(testName = "Integer Bitmask") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllSet("a", 50))); } - @Test + @Test(testName = "BinData Bitmask") public void testExample3() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAllSet("a", new byte[] { 48 }))); diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnyClear.java b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnyClear.java index 80fb9ce1376..c04483d43b9 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnyClear.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnyClear.java @@ -7,19 +7,19 @@ import static dev.morphia.query.filters.Filters.bitsAnyClear; public class TestBitsAnyClear extends FilterTest { - @Test + @Test(testName = "Bit Position Array") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnyClear("a", new int[] { 1, 5 }))); } - @Test + @Test(testName = "Integer Bitmask") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnyClear("a", 35))); } - @Test + @Test(testName = "BinData Bitmask") public void testExample3() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnyClear("a", new byte[] { 48 }))); diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnySet.java b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnySet.java index 71c75f92c19..da34ea2df14 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnySet.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestBitsAnySet.java @@ -7,19 +7,19 @@ import static dev.morphia.query.filters.Filters.bitsAnySet; public class TestBitsAnySet extends FilterTest { - @Test + @Test(testName = "Bit Position Array") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnySet("a", new int[] { 1, 5 }))); } - @Test + @Test(testName = "Integer Bitmask") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnySet("a", 35))); } - @Test + @Test(testName = "BinData Bitmask") public void testExample3() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( bitsAnySet("a", new byte[] { 48 }))); diff --git a/core/src/test/java/dev/morphia/test/query/filters/TestElemMatch.java b/core/src/test/java/dev/morphia/test/query/filters/TestElemMatch.java index 2c4508a95c4..97eff8cba39 100644 --- a/core/src/test/java/dev/morphia/test/query/filters/TestElemMatch.java +++ b/core/src/test/java/dev/morphia/test/query/filters/TestElemMatch.java @@ -10,19 +10,19 @@ import static dev.morphia.query.filters.Filters.lt; public class TestElemMatch extends FilterTest { - @Test(description = "Element Match") + @Test(testName = "Element Match") public void testExample1() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( elemMatch("results", gte(80), lt(85)))); } - @Test + @Test(testName = "Array of Embedded Documents") public void testExample2() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( elemMatch("results", eq("product", "xyz"), gte("score", 8)))); } - @Test + @Test(testName = "Single Query Condition") public void testExample3() { testQuery(ServerVersion.ANY, false, true, (query) -> query.filter( elemMatch("results", eq("product", "xyz")))); diff --git a/docs/antora.yml b/docs/antora.yml index 4ce15a0082d..93a12dac119 100644 --- a/docs/antora.yml +++ b/docs/antora.yml @@ -2,10 +2,9 @@ name: "morphia" title: "Morphia" version: "3.0" -prerelease: "-SNAPSHOT" nav: - "modules/ROOT/nav.adoc" asciidoc: attributes: - version: "3.0.0-SNAPSHOT" - srcRef: "https://github.com/MorphiaOrg/morphia/blob/master" \ No newline at end of file + version: "3.0.0" + srcRef: "https://github.com/MorphiaOrg/morphia/tree/3.0.x" \ No newline at end of file