diff --git a/gradle.properties b/gradle.properties index 750a0f4..66d2cf2 100644 --- a/gradle.properties +++ b/gradle.properties @@ -1,5 +1,5 @@ logbackVersion = 1.2.3 -serenityCoreVersion = 2.3.8 +serenityCoreVersion = 2.3.9 junit5Version = 5.7.0 junitTestKitVersion = 1.7.0 assertJVersion = 3.13.2 diff --git a/serenity-junit5-starter/src/test/java/starter/Junit5TagTest.java b/serenity-junit5-starter/src/test/java/starter/Junit5TagTest.java index e0fcec5..29bd491 100644 --- a/serenity-junit5-starter/src/test/java/starter/Junit5TagTest.java +++ b/serenity-junit5-starter/src/test/java/starter/Junit5TagTest.java @@ -45,8 +45,7 @@ void shouldHaveTwoSimpleTagsViaGroup() { @Test @Tag("junit5Tag") @WithTag("serenityTag") - // TODO until https://github.com/fabianlinz/serenity-junit5/issues/21 is fixed Serenity tag annotation are only considered on public methods - public void shouldAllowUsageOfSerenityAndJunit5TagsTogether() { + void shouldAllowUsageOfSerenityAndJunit5TagsTogether() { // does not make sense though } @@ -58,7 +57,7 @@ void junit5FeatureTag() { @Test @WithTag(name = "serenityFeatureTag") - public void serenityFeatureTag() { + void serenityFeatureTag() { // does not make sense though } diff --git a/serenity-junit5-starter/src/test/java/starter/PureJunit5Test.java b/serenity-junit5-starter/src/test/java/starter/PureJunit5Test.java index b9fff3b..3ddcd3a 100755 --- a/serenity-junit5-starter/src/test/java/starter/PureJunit5Test.java +++ b/serenity-junit5-starter/src/test/java/starter/PureJunit5Test.java @@ -1,8 +1,7 @@ package starter; import net.serenitybdd.junit5.SerenityTest; -import net.thucydides.core.annotations.Manual; -import net.thucydides.core.model.TestResult; +import net.thucydides.core.annotations.Title; import org.junit.jupiter.api.Test; import static org.junit.jupiter.api.Assumptions.assumeTrue; @@ -27,4 +26,9 @@ void successfulTest() { assumeTrue(true); } + @Test + @Title("An explicit title for the test.") + void testWithTitle() { + + } } diff --git a/serenity-junit5/src/main/java/net/thucydides/core/reflection/StackTraceAnalyser.java b/serenity-junit5/src/main/java/net/thucydides/core/reflection/StackTraceAnalyser.java deleted file mode 100644 index 5d6a1e3..0000000 --- a/serenity-junit5/src/main/java/net/thucydides/core/reflection/StackTraceAnalyser.java +++ /dev/null @@ -1,159 +0,0 @@ -// WORKAROUND for https://github.com/serenity-bdd/serenity-core/issues/2229 -package net.thucydides.core.reflection; - -import net.serenitybdd.core.collect.NewList; -import org.apache.commons.lang3.StringUtils; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.lang.reflect.Method; -import java.util.ArrayList; -import java.util.List; -import java.util.Optional; -import java.util.stream.Collectors; - -import static java.util.Arrays.stream; - -public class StackTraceAnalyser { - - private final StackTraceElement stackTraceElement; - private final Logger logger = LoggerFactory.getLogger(StackTraceAnalyser.class); - - private StackTraceAnalyser(StackTraceElement stackTraceElement) { - this.stackTraceElement = stackTraceElement; - } - - public static StackTraceAnalyser forStackTraceElement(StackTraceElement stackTraceElement) { - return new StackTraceAnalyser(stackTraceElement); - } - - public Method getMethod() { - try { - if (allowedClassName(stackTraceElement.getClassName()) && !lambda(stackTraceElement.getClassName())) { - Class callingClass = Class.forName(stackTraceElement.getClassName()); - - if (stackTraceElement.getClassName().contains("$")) { - callingClass = callingClass.getSuperclass(); - if (callingClass == null) { - logger.trace("Ignored class without superclass: " + stackTraceElement.getClassName()); - return null; - } - } - return extractMethod(stackTraceElement, callingClass); - } - } catch (ClassNotFoundException classNotFoundIgnored) { - logger.trace("Couldn't find class during Stack analysis: " + classNotFoundIgnored.getLocalizedMessage()); - } catch (NoClassDefFoundError noClassDefFoundErrorIgnored) { - logger.trace("Couldn't find class definition during Stack analysis: " + noClassDefFoundErrorIgnored.getLocalizedMessage()); - } - return null; - } - - public Method getUnfilteredMethod() { - try { - Class callingClass = Class.forName(stackTraceElement.getClassName()); - Method matchingMethod = extractMethod(stackTraceElement, callingClass); - if (matchingMethod != null) { - return matchingMethod; - } - } catch (ClassNotFoundException classNotFoundIgnored) { - logger.debug("Couldn't find class during Stack analysis: " + classNotFoundIgnored.getLocalizedMessage()); - } catch (NoClassDefFoundError noClassDefFoundErrorIgnored) { - logger.debug("Couldn't find class definition during Stack analysis: " + noClassDefFoundErrorIgnored.getLocalizedMessage()); - } - return null; - } - - private boolean lambda(String className) { - return className.contains("$$Lambda$"); - } - - public static Method extractMethod(StackTraceElement stackTraceElement, Class callingClass) { - Class targetClass; - if (isInstrumentedMethod(stackTraceElement)) { - targetClass = callingClass.getSuperclass(); - } else { - targetClass = callingClass; - } - try { - Method methodFound = targetClass.getMethod(stackTraceElement.getMethodName()); - if (methodFound == null) { - methodFound = targetClass.getDeclaredMethod(stackTraceElement.getMethodName()); - } - return methodFound; - } catch (NoSuchMethodException e) { - return null; - } - } - - private static boolean isInstrumentedMethod(StackTraceElement stackTraceElement) { - return StringUtils.isNotEmpty(stackTraceElement.getFileName()) && (stackTraceElement.getFileName().equals("")); - } - - private final static List HIDDEN_PACKAGES = NewList.of("sun.", "java", "org.gradle"); - - private boolean allowedClassName(String className) { - if (className.contains("$$")) { - return false; - } - if (inHiddenPackage(className)) { - return false; - } - - return true; - } - - private boolean inHiddenPackage(String className) { - for (String hiddenPackage : HIDDEN_PACKAGES) { - if (className.startsWith(hiddenPackage)) { - return true; - } - } - return false; - } - - public static List inscopeMethodsIn(StackTraceElement[] stackTrace) { - List methods = new ArrayList<>(); - for (StackTraceElement stackTraceElement : stackTrace) { - Method method = StackTraceAnalyser.forStackTraceElement(stackTraceElement).getMethod(); - if (method != null) { - methods.add(method); - } - } - return methods; - } - - public static List performAsMethodsIn(StackTraceElement[] stackTrace) { - return stream(stackTrace) - .filter(stackTraceElement -> stackTraceElement.getMethodName().equals("performAs")) - .map(StackTraceElement::getClassName) - .map(StackTraceAnalyser::uninstrumentedTaskClass) - .filter(Optional::isPresent) - .map(StackTraceAnalyser::performAsMethod) - .filter(Optional::isPresent) - .map(Optional::get) - .collect(Collectors.toList()); - } - - private static Optional performAsMethod(Optional> taskClass) { - return stream(taskClass.get().getMethods()) - .filter(method -> method.getName().equals("performAs")) - .findFirst(); - } - - private static Optional> uninstrumentedTaskClass(String taskClassName) { - try { - Class performingClass = Thread.currentThread().getContextClassLoader().loadClass(taskClassName); - while (isInstrumented(performingClass)) { - performingClass = performingClass.getSuperclass(); - } - return Optional.of(performingClass); - } catch (ClassNotFoundException e) { - return Optional.empty(); - } - } - - private static boolean isInstrumented(Class performingClass) { - return performingClass.getName().contains("$"); - } -} diff --git a/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTaggedTests.java b/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTaggedTests.java index 847cce6..7109e65 100644 --- a/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTaggedTests.java +++ b/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTaggedTests.java @@ -120,8 +120,7 @@ static class UsageOfSerenityAndJunit5TagsTogether { @WithTag("serenityTag"), @WithTag(name = "serenityFeatureTag") }) - // TODO until https://github.com/fabianlinz/serenity-junit5/issues/21 is fixed Serenity tag annotation are only considered on public methods - public void test() { + void test() { } } diff --git a/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTitleTests.java b/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTitleTests.java new file mode 100644 index 0000000..4e07ca9 --- /dev/null +++ b/serenity-junit5/src/test/java/net/serenitybdd/junit5/extension/WhenRunningTitleTests.java @@ -0,0 +1,32 @@ +package net.serenitybdd.junit5.extension; + +import net.serenitybdd.junit5.extension.testsupport.SerenityExtensionInnerTest; +import net.serenitybdd.junit5.extension.testsupport.SerenityExtensionTest; +import net.thucydides.core.annotations.Steps; +import net.thucydides.core.annotations.Title; +import org.junit.jupiter.api.Test; + +@SerenityExtensionTest +class WhenRunningTitleTests { + + @Steps + private JUnit5Steps junit5; + + @Test + void the_outcome_should_honor_the_declared_title() { + // when + junit5.executesTestClass(TestWithTitle.class); + + // then + junit5.shouldHaveExactlyOneTestOutcome(); + junit5.outcomeShouldHaveTitle("explicit test title"); + } + + @SerenityExtensionInnerTest + static class TestWithTitle { + @Test + @Title("explicit test title") + void testWithTitle() { + } + } +}