1   /*
2    * Copyright 2001-2004 The Apache Software Foundation.
3    * 
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    * 
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    * 
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */ 
16  
17  package org.apache.commons.logging;
18  
19  
20  import java.io.File;
21  import java.lang.reflect.Method;
22  import java.net.URL;
23  import java.net.URLClassLoader;
24  import java.util.ArrayList;
25  import java.util.List;
26  
27  
28  /***
29   * <p>Wrapper around test cases that need to have a custom class loader
30   * hierarchy assembled.  The wrapper is configured by the following
31   * system properties:</p>
32   * <ul>
33   * <li><strong>wrapper.hierarchy</strong> - Descriptive code describing how
34   *     the class loader hierarchy should be assembled:
35   *     <ul>
36   *     <li><strong>API</strong> - Parent class loader contains
37   *         <code>commons-logging-api.jar</code> and child class loader
38   *         contains <code>commons-logging.jar</code>.  This is like the
39   *         default configuration for Tomcat 4.1.</li>
40   *     <li><strong>FULL</strong> - Parent class loader contains
41   *         <code>commons-logging.jar</code>.  This is what would happen
42   *         if you replaced <code>commons-logging-api.jar</code> with
43   *         <code>commons-logging.jar</code> so that you did not need to
44   *         include the latter with your application.</li>
45   *     </ul>
46   *     The child class loader also unconditionally includes
47   *     <code>commons-logging-tests.jar</code>.</li>
48   * <li><strong>wrapper.junit</strong> - Fully qualified pathname of the
49   *     JUnit JAR file.</li>
50   * <li><strong>wrapper.log4j</strong> - Fully qualified pathname of the
51   *     Log4J JAR file, which will be placed in whichever class loader
52   *     <code>commons-logging.jar</code> is placed in, if specified.</li>
53   * <li><strong>wrapper.target</strong> - Fully qualified pathname of the
54   *     "target" directory created by the build process.  This directory
55   *     must contain the <code>commons-logging.jar</code>,
56   *     <code>commons-logging-api.jar</code>, and
57   *     <code>commons-logging-tests.jar</code> files resulting from the
58   *     execution of the <code>compile.tests</code> target.</li>
59   * <li><strong>wrapper.testcase</strong> - Fully qualified Java class name
60   *     of a TestCase that will ultimately be executed.  This class must
61   *     exist in the <code>commons-logging-tests.jar</code> file.</li>
62   * </ul>
63   *
64   * <p>When executed, the system classpath for the wrapper should include
65   * only the wrapper class itself.</p>
66   *
67   * @author Craig R. McClanahan
68   * @version $Revision: 1.5 $ $Date: 2004/02/28 21:46:45 $
69   */
70  
71  public class Wrapper {
72  
73  
74      public static void main(String args[]) {
75  
76          try {
77  
78              // Create variables we will need
79              List parentList = new ArrayList();
80              List childList = new ArrayList();
81              URL urls[] = null;
82  
83              // Construct URLs for the various JAR files
84              File target = new File(System.getProperty("wrapper.target"));
85              URL commonsLogging =
86                  (new File(target, "commons-logging.jar")).toURL();
87              URL commonsLoggingApi =
88                  (new File(target, "commons-logging-api.jar")).toURL();
89              URL commonsLoggingTests =
90                  (new File(target, "commons-logging-tests.jar")).toURL();
91              URL junit =
92                  (new File(System.getProperty("wrapper.junit"))).toURL();
93              URL appender = null;
94              URL log4j = null;
95              if (System.getProperty("wrapper.log4j") != null) {
96                  log4j =
97                      (new File(System.getProperty("wrapper.log4j"))).toURL();
98                  appender =
99                      (new File(target, "commons-logging-appender.jar")).toURL();
100             }
101 
102             // Construct class loader repository lists for supported scenarios
103             if ("API".equals(System.getProperty("wrapper.hierarchy"))) {
104                 parentList.add(commonsLoggingApi);
105                 childList.add(commonsLogging);
106                 if (log4j != null) {
107                     childList.add(log4j);
108                     childList.add(appender);
109                 }
110             } else { // Assumes "FULL"
111                 parentList.add(commonsLogging);
112                 if (log4j != null) {
113                     parentList.add(log4j);
114                     childList.add(appender);
115                 }
116             }
117             childList.add(commonsLoggingTests);
118             childList.add(junit);
119 
120             // Construt the parent and child class loaders
121             urls = (URL[]) parentList.toArray(new URL[parentList.size()]);
122             ClassLoader parent =
123                 new URLClassLoader(urls,
124                                    ClassLoader.getSystemClassLoader());
125             urls = (URL[]) childList.toArray(new URL[childList.size()]);
126             ClassLoader child = new URLClassLoader(urls, parent);
127 
128             // Execute the test runner for this TestCase
129             ClassLoader old = Thread.currentThread().getContextClassLoader();
130             Thread.currentThread().setContextClassLoader(child);
131             Class clazz = child.loadClass("junit.textui.TestRunner");
132             String params[] = new String[1];
133             params[0] = System.getProperty("wrapper.testcase");
134             Method method = clazz.getMethod("main",
135                                             new Class[] { params.getClass() });
136             method.invoke(null, new Object[] { params });
137             Thread.currentThread().setContextClassLoader(old);
138 
139         } catch (Exception e) {
140 
141             System.out.println("Wrapper Exception Occurred:  " + e);
142             e.printStackTrace(System.out);
143             System.exit(1);
144 
145         }
146 
147     }
148 
149 
150 
151 }