Home | History | Annotate | Download | only in junit3
      1 package android.support.test.internal.runner.junit3;
      2 
      3 import junit.extensions.TestDecorator;
      4 import junit.framework.AssertionFailedError;
      5 import junit.framework.Test;
      6 import junit.framework.TestCase;
      7 import junit.framework.TestListener;
      8 import junit.framework.TestResult;
      9 import junit.framework.TestSuite;
     10 
     11 import org.junit.runner.Describable;
     12 import org.junit.runner.Description;
     13 import org.junit.runner.Runner;
     14 import org.junit.runner.manipulation.Filter;
     15 import org.junit.runner.manipulation.Filterable;
     16 import org.junit.runner.manipulation.NoTestsRemainException;
     17 import org.junit.runner.manipulation.Sortable;
     18 import org.junit.runner.manipulation.Sorter;
     19 import org.junit.runner.notification.Failure;
     20 import org.junit.runner.notification.RunNotifier;
     21 
     22 import java.lang.annotation.Annotation;
     23 import java.lang.reflect.Method;
     24 
     25 // this is a virtually identical copy of org.junit.internal.runner.JUnit38ClassRunner
     26 // from junit 4.12-snapshot. Copied here so android.support.test can work
     27 // with JUnit 4.10+ and pick up the annotation filtering fixes made in 4.12.
     28 public class JUnit38ClassRunner extends Runner implements Filterable, Sortable {
     29     private static final class OldTestClassAdaptingListener implements
     30     TestListener {
     31         private final RunNotifier fNotifier;
     32 
     33         private OldTestClassAdaptingListener(RunNotifier notifier) {
     34             fNotifier = notifier;
     35         }
     36 
     37         @Override
     38         public void endTest(Test test) {
     39             fNotifier.fireTestFinished(asDescription(test));
     40         }
     41 
     42         @Override
     43         public void startTest(Test test) {
     44             fNotifier.fireTestStarted(asDescription(test));
     45         }
     46 
     47         // Implement junit.framework.TestListener
     48         @Override
     49         public void addError(Test test, Throwable t) {
     50             Failure failure = new Failure(asDescription(test), t);
     51             fNotifier.fireTestFailure(failure);
     52         }
     53 
     54         private Description asDescription(Test test) {
     55             if (test instanceof Describable) {
     56                 Describable facade = (Describable) test;
     57                 return facade.getDescription();
     58             }
     59             if (test instanceof TestCase) {
     60                 return makeDescription(test);
     61             }
     62             return Description.createTestDescription(getEffectiveClass(test), test.toString());
     63         }
     64 
     65         private Class<? extends Test> getEffectiveClass(Test test) {
     66             return test.getClass();
     67         }
     68 
     69         @Override
     70         public void addFailure(Test test, AssertionFailedError t) {
     71             addError(test, t);
     72         }
     73     }
     74 
     75     private volatile Test fTest;
     76 
     77     public JUnit38ClassRunner(Class<?> klass) {
     78         this(new TestSuite(klass.asSubclass(TestCase.class)));
     79     }
     80 
     81     public JUnit38ClassRunner(Test test) {
     82         super();
     83         setTest(test);
     84     }
     85 
     86     @Override
     87     public void run(RunNotifier notifier) {
     88         TestResult result = new TestResult();
     89         result.addListener(createAdaptingListener(notifier));
     90         getTest().run(result);
     91     }
     92 
     93     public TestListener createAdaptingListener(final RunNotifier notifier) {
     94         return new OldTestClassAdaptingListener(notifier);
     95     }
     96 
     97     @Override
     98     public Description getDescription() {
     99         return makeDescription(getTest());
    100     }
    101 
    102     // android-changed - change from private so it can be accessed when filtering AndroidTestSuites
    103     static Description makeDescription(Test test) {
    104         if (test instanceof TestCase) {
    105             TestCase tc = (TestCase) test;
    106             return Description.createTestDescription(tc.getClass(), tc.getName(),
    107                     getAnnotations(tc));
    108         } else if (test instanceof TestSuite) {
    109             TestSuite ts = (TestSuite) test;
    110             String name = ts.getName() == null ? createSuiteDescription(ts) : ts.getName();
    111             Description description = Description.createSuiteDescription(name);
    112             int n = ts.testCount();
    113             for (int i = 0; i < n; i++) {
    114                 Description made = makeDescription(ts.testAt(i));
    115                 description.addChild(made);
    116             }
    117             return description;
    118         } else if (test instanceof Describable) {
    119             Describable adapter = (Describable) test;
    120             return adapter.getDescription();
    121         } else if (test instanceof TestDecorator) {
    122             TestDecorator decorator = (TestDecorator) test;
    123             return makeDescription(decorator.getTest());
    124         } else {
    125             // This is the best we can do in this case
    126             return Description.createSuiteDescription(test.getClass());
    127         }
    128     }
    129 
    130     /**
    131      * Get the annotations associated with given TestCase.
    132      * @param test the TestCase.
    133      */
    134     private static Annotation[] getAnnotations(TestCase test) {
    135         try {
    136             Method m = test.getClass().getMethod(test.getName());
    137             return m.getDeclaredAnnotations();
    138         } catch (SecurityException e) {
    139         } catch (NoSuchMethodException e) {
    140         }
    141         return new Annotation[0];
    142     }
    143 
    144     private static String createSuiteDescription(TestSuite ts) {
    145         int count = ts.countTestCases();
    146         String example = count == 0 ? "" : String.format(" [example: %s]", ts.testAt(0));
    147         return String.format("TestSuite with %s tests%s", count, example);
    148     }
    149 
    150     @Override
    151     public void filter(Filter filter) throws NoTestsRemainException {
    152         if (getTest() instanceof Filterable) {
    153             Filterable adapter = (Filterable) getTest();
    154             adapter.filter(filter);
    155         } else if (getTest() instanceof TestSuite) {
    156             TestSuite suite = (TestSuite) getTest();
    157             TestSuite filtered = new TestSuite(suite.getName());
    158             int n = suite.testCount();
    159             for (int i = 0; i < n; i++) {
    160                 Test test = suite.testAt(i);
    161                 if (filter.shouldRun(makeDescription(test))) {
    162                     filtered.addTest(test);
    163                 }
    164             }
    165             setTest(filtered);
    166             if (filtered.testCount() == 0) {
    167                 throw new NoTestsRemainException();
    168             }
    169         }
    170     }
    171 
    172     @Override
    173     public void sort(Sorter sorter) {
    174         if (getTest() instanceof Sortable) {
    175             Sortable adapter = (Sortable) getTest();
    176             adapter.sort(sorter);
    177         }
    178     }
    179 
    180     private void setTest(Test test) {
    181         fTest = test;
    182     }
    183 
    184     private Test getTest() {
    185         return fTest;
    186     }
    187 }
    188