View Javadoc
1   /*
2    * Redistribution and use of this software and associated documentation
3    * ("Software"), with or without modification, are permitted provided
4    * that the following conditions are met:
5    *
6    * 1. Redistributions of source code must retain copyright
7    *    statements and notices.  Redistributions must also contain a
8    *    copy of this document.
9    *
10   * 2. Redistributions in binary form must reproduce the
11   *    above copyright notice, this list of conditions and the
12   *    following disclaimer in the documentation and/or other
13   *    materials provided with the distribution.
14   *
15   * 3. The name "Exolab" must not be used to endorse or promote
16   *    products derived from this Software without prior written
17   *    permission of Intalio, Inc.  For written permission,
18   *    please contact info@exolab.org.
19   *
20   * 4. Products derived from this Software may not be called "Exolab"
21   *    nor may "Exolab" appear in their names without prior written
22   *    permission of Intalio, Inc. Exolab is a registered
23   *    trademark of Intalio, Inc.
24   *
25   * 5. Due credit should be given to the Exolab Project
26   *    (http://www.exolab.org/).
27   *
28   * THIS SOFTWARE IS PROVIDED BY INTALIO, INC. AND CONTRIBUTORS
29   * ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT
30   * NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
31   * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL
32   * INTALIO, INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
33   * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
34   * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
35   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
36   * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
37   * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
38   * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
39   * OF THE POSSIBILITY OF SUCH DAMAGE.
40   *
41   * Copyright 2001-2002 (C) Intalio, Inc. All Rights Reserved.
42   *
43   * $Id: TestCaseAggregator.java 6787 2007-01-29 06:00:49Z ekuns $
44   */
45  package org.castor.xmlctf;
46  
47  import java.io.File;
48  
49  import org.castor.xmlctf.util.FileServices;
50  
51  
52  import junit.framework.Test;
53  import junit.framework.TestCase;
54  import junit.framework.TestSuite;
55  
56  /**
57   * This class is used to inspect recursively a hierarchy of directories that
58   * contain CTF tests (jars or directories). A JUnit TestSuite is created for
59   * each directory.
60   *
61   * @author <a href="mailto:gignoux@kernelcenter.org">Sebastien Gignoux</a>
62   * @author <a href="mailto:blandin@intalio.com">Arnaud Blandin</a>
63   * @version $Revision: 6787 $ $Date: 2006-04-26 15:14:53 -0600 (Wed, 26 Apr 2006) $
64   */
65  public class TestCaseAggregator extends TestCase {
66  
67      /** File separator for this system. */
68      private static final String FILE_SEPARATOR = System.getProperty("file.separator");
69      /** Name of the system property to set up the verbose mode. */
70      public static final String VERBOSE_PROPERTY = "org.exolab.castor.tests.Verbose";
71      /** Name of the system property to set up the printStackTrace mode. */
72      public static final String PRINT_STACK_TRACE = "org.exolab.castor.tests.printStack";
73      /** True if we desire a lot of info on what happen. */
74      private static boolean _verbose;
75  
76      static {
77          String v = System.getProperty(VERBOSE_PROPERTY);
78          _verbose = (v != null && v.equals("true"));
79      }
80  
81      /** The directory that contains CTF test cases. */
82      private final File _directory;
83      /** Location of the temporary files when the tests are run. */
84      private final String _testOutputRoot;
85      /** String containing the directory path from the test root to here. */
86      private final String _directoryToHere;
87  
88      /**
89       * Creates a new TestCaseAggregator with the given name.
90       *
91       * @param name the name of this TestCaseAggregator
92       */
93      public TestCaseAggregator(final String name) {
94          super(name);
95          _directory       = null;
96          _directoryToHere = null;
97          _testOutputRoot  = null;
98      }
99  
100     /**
101      * Create a new TestCaseAggregator which will inspect the directory given in
102      * parameter.
103      *
104      * @param directory the directory to inspect for test case and subdirectory
105      * @param testOutputRoot the path to the directory where the test in this
106      *            directory can put there temporary files.
107      */
108     public TestCaseAggregator(final File directory, final String testOutputRoot) {
109         super(directory.getName());
110         _directory       = directory;
111         _directoryToHere = "";
112         _testOutputRoot  = testOutputRoot;
113     }
114 
115     /**
116      * Create a new TestCaseAggregator which will inspect the directory given in
117      * parameter.
118      *
119      * @param directory the directory to inspect for test case and subdirectory
120      * @param directoryToHere the directory path above "directory"
121      * @param testOutputRoot the path to the directory where the test in this
122      *            directory can put there temporary files.
123      */
124     protected TestCaseAggregator(final File directory, final String directoryToHere,
125                                  final String testOutputRoot) {
126         super(directory.getName());
127         _directory       = directory;
128         _directoryToHere = directoryToHere + "/";
129         _testOutputRoot  = testOutputRoot;
130     }
131 
132     /**
133      * Assembles and returns a test suite containing all known tests.
134      *
135      * @return A non-null test suite.
136      */
137     public Test suite() {
138         final TestSuite suite = new TestSuite();
139         final String suiteName = (_directoryToHere.length() == 0) ? _directory.getName()
140                                                                   : _directoryToHere;
141         suite.setName(suiteName);
142 
143         if (!_directory.isDirectory()) {
144             // Maybe it is a jar file, it happens if we run the
145             // CastorTestSuiteRunner with just one jar in param
146             if (_directory.getName().endsWith(".jar")) {
147                 CastorTestCase tc = new CastorTestCase(_directory, _directoryToHere, _testOutputRoot);
148                 return tc.suite();
149             }
150             // If not a jar file, just return the empty TestSuite
151             return suite;
152         }
153 
154         String outputRoot = _testOutputRoot;
155         if (outputRoot.endsWith("/") || outputRoot.endsWith(FILE_SEPARATOR)) {
156             outputRoot = outputRoot + _directory.getName();
157         } else {
158             outputRoot = outputRoot + FILE_SEPARATOR + _directory.getName();
159         }
160 
161         verbose("\n==================================================================");
162         verbose("Processing directory:\n" + _directory.getAbsolutePath());
163         verbose("==================================================================\n");
164 
165         final File[] list = _directory.listFiles();
166         for (int i = 0; i < list.length; ++i) {
167             processOneFileOrDirectory(suite, outputRoot, list[i]);
168         }
169 
170         return suite;
171     }
172 
173     /**
174      * Processes a single file or directory, recurses into directories and for
175      * files, if a JAR file or a test descriptor XML file, create a new test
176      * case and add it to our test suite.
177      *
178      * @param suite the test suite to add new tests to
179      * @param outputRoot output directory for temporary files in our tests
180      * @param file the file or directory to process
181      */
182     private void processOneFileOrDirectory(final TestSuite suite, final String outputRoot,
183                                            final File file) {
184         String name = file.getName();
185 
186         // If a directory (and not a source control directory), recurse
187         if (file.isDirectory()) {
188             // Directories that contain TestDescriptor.xml do not get recursed any deeper
189             if (!FileServices.isScmDirectory(name) && !((new File(file.getParentFile(), "TestDescriptor.xml")).exists())) {
190                 //look for jars or testDescriptor files inside the directory
191                 Test test = new TestCaseAggregator(file, _directoryToHere + file.getName(), outputRoot).suite();
192                 if (test != null) {
193                     suite.addTest(test);
194                 }
195             }
196             return;
197         }
198 
199         // Otherwise make a test case if a JAR file or test descriptor
200 
201         Test test = null;
202         if (name.endsWith(".jar")) {
203             test = (new CastorTestCase(file, _directoryToHere, outputRoot)).suite();
204         } else if (name.endsWith(CastorTestCase.TEST_DESCRIPTOR)) {
205             test = (new CastorTestCase(_directory, _directoryToHere, outputRoot)).suite();
206         }
207 
208         if (test != null) {
209             suite.addTest(test);
210         }
211     }
212 
213     /**
214      * Prints the provided message if verbose is true.
215      * @param message the message to print
216      */
217     private void verbose(final String message) {
218         if (_verbose) {
219             System.out.println(message);
220         }
221     }
222 
223 }