testng
testng copied to clipboard
Method predecessors lookup and/or method sorting is broken in certain inheritance and naming setups
⁸### TestNG Version
7.8.0 on JDK 11 Temurin (Liniux and Windows)
maven-surefire-plugin:3.1.2
aspectjweaver:1.9.20.1
Or check out the source code: https://github.com/ptomaszek/testng-pt-playground/tree/feature/testng-7.8.0-unexpected-failure
Expected behavior
Test passes
Actual behavior
Test fails
Is the issue reproducible on runner?
- [X] Shell
- [X] Maven
- [ ] Gradle
- [ ] Ant
- [ ] Eclipse
- [X] IntelliJ
- [ ] NetBeans
Test case sample
Run the test (IntelliJ or mvn test) and note it fails. Then apply any solution from the comments and observe the test passes:
package com.example; // 1. to make the test PASS change to `org.example`
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
import static org.testng.Assert.assertNotNull;
public class MyTest extends MyBaseTest {
@BeforeClass
public void beforeClass() {
assertNotNull(dependency); // fails here
}
@Test
public void test() {
}
}
abstract class MyBaseTest implements MyInterface { // 2. alternatively, to make the test PASS remove `implements MyInterface`
protected Object dependency;
public void setDependency(Object dependency) {
}
@BeforeClass
public void setupDependency() {
dependency = new Object();
}
@BeforeClass(dependsOnMethods = "setupDependency")
public void setupAdditionalDependency_() { // 3. alternatively, to make the test PASS remove `_` from the method name
}
}
interface MyInterface {
void setDependency(Object dependency);
default Object getDependency() { // 4. alternatively, to make the test PASS remove this method
return null;
}
}
Something that may direct you to the solution:
Debug code at Graph:130 (at the end of topologicalSort()) and observe the object's state:
when PASS, you'll see:
m_strictlySortedNodes = {ArrayList@2282} size = 2
0 = {ConfigurationMethod@2292} "MyTest.setupDependency()[pri:0, instance:null]"
1 = {ConfigurationMethod@2293} "MyTest.setupAdditionalDependency()[pri:0, instance:null]"
when FAIL, you'll see
m_strictlySortedNodes = {ArrayList@2283} size = 3
0 = {ConfigurationMethod@2293} "MyTest.beforeClass()[pri:0, instance:null]" // I believe it should not be here, as the list should contain only independent (top level?) methods
1 = {ConfigurationMethod@2294} "MyTest.setupDependency()[pri:0, instance:null]"
2 = {ConfigurationMethod@2295} "MyTest.setupAdditionalDependency_()[pri:0, instance:null]"