Qytera-Gmbh / QTAF

QTAF is a Java test framework based on TestNG and offers easy setup of Selenium and fast extensibility.
https://qytera-gmbh.github.io
MIT License
10 stars 0 forks source link

Test case is still considered successful in the pipeline of Jenkins even by failed steps #311

Open ValeriusSchmidt opened 5 months ago

ValeriusSchmidt commented 5 months ago

Jenkins Log erfolgreicher Konsolen Output

First encounter: Testcase 1386

Method that causes this behaviour in Jenkins: Under notifications, where a list of all pop-up messages is stored

Steps to reproduce

  1. Write a test with @Test annotation that includes expectNotificationTextToContainList("Enter your message(s) here") //Be aware that you need a test which triggeres multiple pop-up windows in a short timeframe
  2. Execute the test using: mvn test
  3. Observe BUILD SUCCESS instead of BUILD FAILURE even though the log contains Test failure or Step failure
OliverHoenig commented 5 months ago

After a one-to-one session with Valerius, the issue could be abstracted as follows:

Within the test case, assertTrue (from QTAF) was called in one step. This step of the test case fails. The following anomalies were found:

It is also not clear whether this is a QTAF bug or whether configurations in the pipeline cause side effects that lead to this behaviour.

The behaviour is now being analysed.

OliverHoenig commented 5 months ago

I have tried to generalise the scenario in which the suspected bug might occur. Here is the class which contains steps:

package de.qytera.tests.issue311;

import de.qytera.qtaf.core.guice.annotations.Step;
import de.qytera.qtaf.testng.context.QtafTestNGContext;

public class DummySteps extends QtafTestNGContext {
    @Step(
            name="dummy Step",
            description = "dummy step for mocking the behavior of issue 311"
    )
    public void trueDummyStep() {
        assertTrue(true, "Step should be true");
    }
    public void falseDummyStep() {
        assertTrue(false, "Step should be true");
    }
}

And a here the used test class:

package de.qytera.tests.issue311;

import de.qytera.qtaf.core.config.annotations.TestFeature;
import de.qytera.qtaf.testng.context.QtafTestNGContext;
import org.testng.annotations.Test;

@TestFeature(
        name = "TestCase One",
        description = "First test"
)
public class Issue311Test extends QtafTestNGContext {

    @Test(testName  = "simplifiedBugScenario", description = "most abstracted scenario the bug could potential occur")
    public void simplifiedBugScenario(){
        DummySteps dummySteps = load(DummySteps.class);
        dummySteps.falseDummyStep();
    }
}

I could not reproduce the bug locally on my device. However, the execution of the above testcase (simplifiedBugScenario()) resulted in a NullPointerException when the test was executed in your project. Remarkably, only if dummySteps.falseDummyStep() was called and not if dummySteps.trueDummyStep() gets called instead in the test case.

There seems to be a NullPointerException in your HtmlDumpSubscriber, which implements IEvenetSubscriber. Inside the method getHtmlDumpDestitnationPath() the following line leads to the following exception:

String name = stepExecutionInfo.getMethodInvocation().getMethod().getName();

java.lang.NullPointerException: Cannot invoke "org.aopalliance.intercept.MethodInvocation.getMethod()" because the return value of "de.qytera.qtaf.core.guice.invokation.StepExecutionInfo.getMethodInvocation()" is null

ValeriusSchmidt commented 5 months ago

To reproduce this behaviour in the pipeline I created a new branch "AssertTestBranch" (without quotes). The test target of reproduction is testcase 1386.

qytera-development commented 3 months ago

The solution is to check whether a class is annotated with the specific listener in the beforeInvocation method:

    public void beforeInvocation(IInvokedMethod invokedMethod, ITestResult result) {
        LocalTime currentTimeUTC = LocalDateTime.now()
                .atZone(ZoneId.systemDefault())
                .withZoneSameInstant(ZoneId.of("UTC+2"))
                .toLocalTime();
        Annotation[] anns = invokedMethod.getTestMethod().getRealClass().getAnnotations();

        // Check if test class has Listener annotations
        for (Annotation ann : anns) {
            if (ann instanceof Listeners) {
                Class<? extends ITestNGListener>[] listeners = ((Listeners) ann).value();
                for (Class<? extends ITestNGListener> listener : listeners) {
                    // Check if one of the Listeners is an instance of BindingClassListener
                    if (listener.equals(BindingGasListener.class)) {
                        if (currentTimeUTC.isBefore(START_TIME)) {
                            throw new SkipException("Binding offer gas tests must be started after %s".formatted(START_TIME.toString()));
                        }
                    }
                }
            }
        }

    }
OliverHoenig commented 2 months ago

@qytera-development Are changes in the QTAF-repo necessary, or did I understand correctly that the changes in your implementation are sufficient? Have the changes already been made, and has this resolved the issue? If yes: Can this issue be closed?