Home | History | Annotate | Download | only in textui
      1 package junit.textui;
      2 
      3 
      4 import java.io.PrintStream;
      5 
      6 import junit.framework.Test;
      7 import junit.framework.TestCase;
      8 import junit.framework.TestResult;
      9 import junit.framework.TestSuite;
     10 import junit.runner.BaseTestRunner;
     11 import junit.runner.Version;
     12 
     13 /**
     14  * A command line based tool to run tests.
     15  * <pre>
     16  * java junit.textui.TestRunner [-wait] TestCaseClass
     17  * </pre>
     18  * <p>
     19  * TestRunner expects the name of a TestCase class as argument.
     20  * If this class defines a static <code>suite</code> method it
     21  * will be invoked and the returned test is run. Otherwise all
     22  * the methods starting with "test" having no arguments are run.
     23  * <p>
     24  * When the wait command line argument is given TestRunner
     25  * waits until the users types RETURN.
     26  * <p>
     27  * TestRunner prints a trace as the tests are executed followed by a
     28  * summary at the end.
     29  */
     30 public class TestRunner extends BaseTestRunner {
     31     private ResultPrinter fPrinter;
     32 
     33     public static final int SUCCESS_EXIT = 0;
     34     public static final int FAILURE_EXIT = 1;
     35     public static final int EXCEPTION_EXIT = 2;
     36 
     37     /**
     38      * Constructs a TestRunner.
     39      */
     40     public TestRunner() {
     41         this(System.out);
     42     }
     43 
     44     /**
     45      * Constructs a TestRunner using the given stream for all the output
     46      */
     47     public TestRunner(PrintStream writer) {
     48         this(new ResultPrinter(writer));
     49     }
     50 
     51     /**
     52      * Constructs a TestRunner using the given ResultPrinter all the output
     53      */
     54     public TestRunner(ResultPrinter printer) {
     55         fPrinter = printer;
     56     }
     57 
     58     /**
     59      * Runs a suite extracted from a TestCase subclass.
     60      */
     61     static public void run(Class<? extends TestCase> testClass) {
     62         run(new TestSuite(testClass));
     63     }
     64 
     65     /**
     66      * Runs a single test and collects its results.
     67      * This method can be used to start a test run
     68      * from your program.
     69      * <pre>
     70      * public static void main (String[] args) {
     71      *    test.textui.TestRunner.run(suite());
     72      * }
     73      * </pre>
     74      */
     75     static public TestResult run(Test test) {
     76         TestRunner runner = new TestRunner();
     77         return runner.doRun(test);
     78     }
     79 
     80     /**
     81      * Runs a single test and waits until the user
     82      * types RETURN.
     83      */
     84     static public void runAndWait(Test suite) {
     85         TestRunner aTestRunner = new TestRunner();
     86         aTestRunner.doRun(suite, true);
     87     }
     88 
     89     @Override
     90     public void testFailed(int status, Test test, Throwable e) {
     91     }
     92 
     93     @Override
     94     public void testStarted(String testName) {
     95     }
     96 
     97     @Override
     98     public void testEnded(String testName) {
     99     }
    100 
    101     /**
    102      * Creates the TestResult to be used for the test run.
    103      */
    104     protected TestResult createTestResult() {
    105         return new TestResult();
    106     }
    107 
    108     public TestResult doRun(Test test) {
    109         return doRun(test, false);
    110     }
    111 
    112     public TestResult doRun(Test suite, boolean wait) {
    113         TestResult result = createTestResult();
    114         result.addListener(fPrinter);
    115         long startTime = System.currentTimeMillis();
    116         suite.run(result);
    117         long endTime = System.currentTimeMillis();
    118         long runTime = endTime - startTime;
    119         fPrinter.print(result, runTime);
    120 
    121         pause(wait);
    122         return result;
    123     }
    124 
    125     protected void pause(boolean wait) {
    126         if (!wait) return;
    127         fPrinter.printWaitPrompt();
    128         try {
    129             System.in.read();
    130         } catch (Exception e) {
    131         }
    132     }
    133 
    134     public static void main(String args[]) {
    135         TestRunner aTestRunner = new TestRunner();
    136         try {
    137             TestResult r = aTestRunner.start(args);
    138             if (!r.wasSuccessful()) {
    139                 System.exit(FAILURE_EXIT);
    140             }
    141             System.exit(SUCCESS_EXIT);
    142         } catch (Exception e) {
    143             System.err.println(e.getMessage());
    144             System.exit(EXCEPTION_EXIT);
    145         }
    146     }
    147 
    148     /**
    149      * Starts a test run. Analyzes the command line arguments and runs the given
    150      * test suite.
    151      */
    152     public TestResult start(String args[]) throws Exception {
    153         String testCase = "";
    154         String method = "";
    155         boolean wait = false;
    156 
    157         for (int i = 0; i < args.length; i++) {
    158             if (args[i].equals("-wait")) {
    159                 wait = true;
    160             } else if (args[i].equals("-c")) {
    161                 testCase = extractClassName(args[++i]);
    162             } else if (args[i].equals("-m")) {
    163                 String arg = args[++i];
    164                 int lastIndex = arg.lastIndexOf('.');
    165                 testCase = arg.substring(0, lastIndex);
    166                 method = arg.substring(lastIndex + 1);
    167             } else if (args[i].equals("-v")) {
    168                 System.err.println("JUnit " + Version.id() + " by Kent Beck and Erich Gamma");
    169             } else {
    170                 testCase = args[i];
    171             }
    172         }
    173 
    174         if (testCase.equals("")) {
    175             throw new Exception("Usage: TestRunner [-wait] testCaseName, where name is the name of the TestCase class");
    176         }
    177 
    178         try {
    179             if (!method.equals("")) {
    180                 return runSingleMethod(testCase, method, wait);
    181             }
    182             Test suite = getTest(testCase);
    183             return doRun(suite, wait);
    184         } catch (Exception e) {
    185             throw new Exception("Could not create and run test suite: " + e);
    186         }
    187     }
    188 
    189     protected TestResult runSingleMethod(String testCase, String method, boolean wait) throws Exception {
    190         Class<? extends TestCase> testClass = loadSuiteClass(testCase).asSubclass(TestCase.class);
    191         Test test = TestSuite.createTest(testClass, method);
    192         return doRun(test, wait);
    193     }
    194 
    195     @Override
    196     protected void runFailed(String message) {
    197         System.err.println(message);
    198         System.exit(FAILURE_EXIT);
    199     }
    200 
    201     public void setPrinter(ResultPrinter printer) {
    202         fPrinter = printer;
    203     }
    204 
    205 
    206 }