Maven的TestNG应用中,由于直接调用TestNG.run(),会很早的实例化test class, 想问把实例化推后点,所以想定制自己的test runners, 如果通过私人定制如下图片中的testrunfactory,还会调用TestNG.run()这个方法吗?
如何定制有哪位童鞋能贴点Java code我吗?多谢!
Maven的TestNG应用中,由于直接调用TestNG.run(),会很早的实例化test class, 想问把实例化推后点,所以想定制自己的test runners, 如果通过私人定制如下图片中的testrunfactory,还会调用TestNG.run()这个方法吗?
如何定制有哪位童鞋能贴点Java code我吗?多谢!
让阿豪来帮你解答,本回答参考chatgpt3.5编写提供,如果还有疑问可以评论或留言问题分析: 该问题的背景是使用Maven的TestNG应用中,当调用TestNG.run()时,test class会被早早地实例化。要推迟实例化时间,需要定制自己的test runners。 对于是否仍会调用TestNG.run()方法的疑问,根据代码逻辑,可能需要查阅TestNG官方文档进行确认。 解答: 为了实现定制化的test runners,需要使用TestNG的IAnnotationTransformer接口和IAnnotationTransformer2接口。使用这些接口可以通过监听@Test注解,实现在测试运行之前或之后,对测试类实例进行控制。 在其中一个接口中,你需要覆盖transform()方法,在另一个中,你还需要覆盖transfromationMap()方法。具体的实现过程可以参考以下代码:
public class CustomTestRunFactory implements ITestRunnerFactory {
@Override
public TestRunner newTestRunner(TestListenerAdapter testListenerAdapter,
Configuration configuration,
XmlSuite xmlSuite) {
return new TestRunner2(testListenerAdapter, configuration, xmlSuite);
}
private static class TestRunner2 extends TestRunner {
TestRunner2(TestListenerAdapter testListenerAdapter, Configuration configuration, XmlSuite xmlSuite) {
super(testListenerAdapter, configuration, xmlSuite);
}
@SuppressWarnings("rawtypes")
@Override
public void run() throws TestException {
for (ITestClass testClass : getTestClasses()) {
ITestContext context = new TestRunnerContext(getTestListeners(),
testClass.getXmlTest(),
testClass,
getTestRunnerOutputDirectory(),
1);
this.invokeListenersStartExecution(context);
Object instance = null;
try {
// 测试类实例化被推迟到测试执行之前
instance = testClass.getRealClass().newInstance();
} catch (InstantiationException | IllegalAccessException e) {
throw new TestException("Could not create test class instance " + testClass.getName(), e);
}
Test test = testClass.getTest();
test.getBeforeTestMethodConfiguration().apply(instance);
for (String m : test.getTestMethods()) {
Method method;
try {
method = testClass.getRealClass().getMethod(m);
} catch (NoSuchMethodException e) {
throw new TestException("Could not find method " + m + " in test class " + testClass.getName(), e);
}
Object[] parameters = new Object[method.getParameterCount()];
RunAfterTestMethodCallbacks runAfterTestMethodCallbacks
= new RunAfterTestMethodCallbacks(getTestListeners(), instance, method);
ITestResult tr = null;
if (method.getParameterCount() == 0) {
tr = createTestResult(testClass.getName(), method);
runTestMethod(instance, tr, method, parameters, runAfterTestMethodCallbacks);
} else {
// code here
}
}
test.getAfterTestMethodConfiguration().apply(instance);
// 执行测试完成的监听操作
this.invokeListenersFinishExecution(context);
}
}
}
@Override public void transform(ITestAnnotation testAnnotation, Class testClass,
Constructor testConstructor, Method testMethod) {
// Override TestNG's default suite name generator
if (testAnnotation.getSuiteName().isEmpty()) {
String fullClassName = testClass.getName();
String packageName = fullClassName.substring(0, fullClassName.lastIndexOf('.'));
testAnnotation.setSuiteName(packageName);
}
}
@SuppressWarnings("rawtypes")
@Override public void transform(IDataProviderAnnotation dataProviderAnnotation, Method method) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(IConfigurationAnnotation iConfigurationAnnotation, Class aClass,
Constructor constructor, Method method) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(IFactoryAnnotation iFactoryAnnotation, Method method) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(IListenersAnnotation iListenersAnnotation, Class aClass) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(ISuiteAnnotation iSuiteAnnotation, Suite suite) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(ITestRunnerAnnotation iTestRunner, Class aClass) {
}
@SuppressWarnings("rawtypes")
@Override public void transform(IParametersAnnotation iParametersAnnotation, Method method) {
}
@Override public Map<Class<? extends ITestNGListener>, Integer> getTestListeners() {
Map<Class<? extends ITestNGListener>, Integer> testListeners = super.getTestListeners();
if (testListeners == null) {
testListeners = new HashMap<>();
}
// add your custom listeners here
testListeners.put(IReporter.class, 3);
return testListeners;
}
}
这个实现方案中,将ITestRunnerFactory中的newTestRunner()方法替换为TestRunner2的实现。在这个实现方案中,测试类的实例化被推迟到测试执行之前。它还实现了IAnnotationTransformer接口,通过监听@Test注解,这个接口可以实现在测试运行之前或之后,对测试类实例进行控制。 参考文献: - http://testng.org/doc/documentation-main.htm#listeners-annotations - http://testng.org/doc/documentation-main.html#testng-faq - http://maven.apache.org/surefire/maven-surefire-plugin/examples/testng.html