前言:
在testerhome社区中,有人评论说直接使用TestNG,就可以实现多线程,是的,但是方式不一样;我们是按照自己的需求对JUnit4自定义多线程Runner,直接在某个类加上相应的注解即可,运行该类就行,支持类和方法级别;TestNG只在方法上有注解 @Test(threadPoolSize = m, invocationCount = n, timeOut = i)实现了对这个方法进行多线程重复跑,threadPoolSize多少个线程执行该方法,invocationCount被执行次数,timeOut每次执行该方法的超时时间,这仅是用多线程重复执行这一个方法,而不是类下面的所有方法同时并发执行,并不是所谓的方法级别并发;TestNG是在xml指定并发的类,方法,组件,具体参照TestNG Executing Parallel Tests Example。
这里不讨论TestNG与JUnit4谁好谁坏,JUnit 4 vs TestNG,只要能满足自己的业务需要即可。
本文仅针对JUnit4进行二次开发。
JUnit4本身是支持多线程,但没有提供多线程的注解;本文将介绍JUnit4自身的多线程实现,自定义对单个类进行多线程执行的Runner和自定义聚合多个类进行多线程执行的Runner。
(一)JUnit4自身的多线程实现
JUnit4提供了ParallerComputer类来使用多线程执行测试用例。
java.lang.Object
extended by org.junit.runner.Computer
extended by org.junit.experimental.ParallelComputer
源码如下:
001 package org.junit.experimental;
002
003 import java.util.concurrent.ExecutorService;
004 import java.util.concurrent.Executors;
005 import java.util.concurrent.TimeUnit;
006
007 import org.junit.runner.Computer;
008 import org.junit.runner.Runner;
009 import org.junit.runners.ParentRunner;
010 import org.junit.runners.model.InitializationError;
011 import org.junit.runners.model.RunnerBuilder;
012 import org.junit.runners.model.RunnerScheduler;
013
014 public class ParallelComputer extends Computer {
015 private final boolean classes;
016
017 private final boolean methods;
018
019 public ParallelComputer(boolean classes, boolean methods) {
020 this.classes = classes;
021 this.methods = methods;
022 }
023
024 public static Computer classes() {
025 return new ParallelComputer(true, false);
026 }
027
028 public static Computer methods() {
029 return new ParallelComputer(false, true);
030 }
031
032 private static Runner parallelize(Runner runner) {
033 if (runner instanceof ParentRunner) {
034 ((ParentRunner<?>) runner).setScheduler(new RunnerScheduler() {
035 private final ExecutorService fService = Executors.newCachedThreadPool();
036
037 public void schedule(Runnable childStatement) {
038 fService.submit(childStatement);
039 }
040
041