在util包中建立RetryFail.java和RetryListener.java两个文件
1 package h5.jddj.util; 2 3 import org.apache.log4j.Logger; 4 import org.testng.IRetryAnalyzer; 5 import org.testng.ITestResult; 6 import org.testng.Reporter; 7 8 public class RetryFail implements IRetryAnalyzer 9 { 10 private static Logger logger = Logger.getLogger(RetryFail.class); 11 private int retryCount = 1; 12 private static int maxRetryCount = 2; 13 // private static ConfigReader config; 14 /* static { 15 //外围文件配置最大运行次数 16 config = new ConfigReader(TestngListener.CONFIG); 17 maxRetryCount = config.getMaxRunCount(); 18 logger.info("maxRunCount=" + (maxRetryCount)); 19 } 20 */ 21 @Override 22 public boolean retry(ITestResult result) { 23 if (retryCount <= maxRetryCount) { 24 String message = "running retry for '" + result.getName() + "' on class " + 25 this.getClass().getName() + " Retrying " + retryCount + " times"; 26 logger.info(message); 27 Reporter.setCurrentTestResult(result); 28 Reporter.log("RunCount=" + (retryCount + 1)); 29 retryCount++; 30 return true; 31 } 32 return false; 33 } 34 35 }
1 package h5.jddj.util; 2 3 import java.lang.reflect.Constructor; 4 import java.lang.reflect.Method; 5 6 import org.testng.IAnnotationTransformer; 7 import org.testng.IRetryAnalyzer; 8 import org.testng.annotations.ITestAnnotation; 9 10 public class RetryListener implements IAnnotationTransformer { 11 12 @SuppressWarnings("rawtypes") 13 @Override 14 public void transform(ITestAnnotation annotation, Class testClass, 15 Constructor testConstructor, Method testMethod) { 16 17 IRetryAnalyzer retry = annotation.getRetryAnalyzer(); 18 if (retry == null) { 19 //annotation.setRetryAnalyzer(RetryAnalyzer.class); 20 annotation.setRetryAnalyzer(RetryFail.class); 21 } 22 } 23 24 }
在用例监听CaseListener.java中添加一下代码:
1 @Override 2 public void onFinish(ITestContext testContext) { 3 super.onFinish(testContext); 4 5 // List of test results which we will delete later 6 ArrayList<ITestResult> testsToBeRemoved = new ArrayList<ITestResult>(); 7 // collect all id's from passed test 8 Set<Integer> passedTestIds = new HashSet<Integer>(); 9 for (ITestResult passedTest : testContext.getPassedTests().getAllResults()) { 10 // logger.info("PassedTests = " + passedTest.getName()); 11 passedTestIds.add(getId(passedTest)); 12 } 13 14 Set<Integer> failedTestIds = new HashSet<Integer>(); 15 for (ITestResult failedTest : testContext.getFailedTests().getAllResults()) { 16 // logger.info("failedTest = " + failedTest.getName()); 17 // id = class + method + dataprovider 18 int failedTestId = getId(failedTest); 19 20 // if we saw this test as a failed test before we mark as to be deleted 21 // or delete this failed test if there is at least one passed version 22 if (failedTestIds.contains(failedTestId) || passedTestIds.contains(failedTestId)) { 23 testsToBeRemoved.add(failedTest); 24 } else { 25 failedTestIds.add(failedTestId); 26 } 27 } 28 29 // finally delete all tests that are marked 30 for (Iterator<ITestResult> iterator = testContext.getFailedTests().getAllResults().iterator(); iterator.hasNext();) { 31 ITestResult testResult = iterator.next(); 32 if (testsToBeRemoved.contains(testResult)) { 33 // logger.info("Remove repeat Fail Test: " + testResult.getName()); 34 iterator.remove(); 35 } 36 } 37 38 } 39 40 private int getId(ITestResult result) { 41 int id = result.getTestClass().getName().hashCode(); 42 id = id + result.getMethod().getMethodName().hashCode(); 43 id = id + (result.getParameters() != null ? Arrays.hashCode(result.getParameters()) : 0); 44 return id; 45 }
最后不要忘记在XML配置文件中引入之前创建的两个文件
<listener class-name="h5.jddj.util.RetryFail"/> <listener class-name="h5.jddj.util.RetryListener"/>