001: /*
002: * $Header: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/BootstrapService.java,v 1.16 2002/07/11 13:47:02 jfclere Exp $
003: * $Revision: 1.16 $
004: * $Date: 2002/07/11 13:47:02 $
005: *
006: * ====================================================================
007: *
008: * The Apache Software License, Version 1.1
009: *
010: * Copyright (c) 1999 The Apache Software Foundation. All rights
011: * reserved.
012: *
013: * Redistribution and use in source and binary forms, with or without
014: * modification, are permitted provided that the following conditions
015: * are met:
016: *
017: * 1. Redistributions of source code must retain the above copyright
018: * notice, this list of conditions and the following disclaimer.
019: *
020: * 2. Redistributions in binary form must reproduce the above copyright
021: * notice, this list of conditions and the following disclaimer in
022: * the documentation and/or other materials provided with the
023: * distribution.
024: *
025: * 3. The end-user documentation included with the redistribution, if
026: * any, must include the following acknowlegement:
027: * "This product includes software developed by the
028: * Apache Software Foundation (http://www.apache.org/)."
029: * Alternately, this acknowlegement may appear in the software itself,
030: * if and wherever such third-party acknowlegements normally appear.
031: *
032: * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software
033: * Foundation" must not be used to endorse or promote products derived
034: * from this software without prior written permission. For written
035: * permission, please contact apache@apache.org.
036: *
037: * 5. Products derived from this software may not be called "Apache"
038: * nor may "Apache" appear in their names without prior written
039: * permission of the Apache Group.
040: *
041: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
042: * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
043: * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
044: * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
045: * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
046: * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
047: * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
048: * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
049: * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
050: * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
051: * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
052: * SUCH DAMAGE.
053: * ====================================================================
054: *
055: * This software consists of voluntary contributions made by many
056: * individuals on behalf of the Apache Software Foundation. For more
057: * information on the Apache Software Foundation, please see
058: * <http://www.apache.org/>.
059: *
060: * [Additional notices, if required by prior licensing conditions]
061: *
062: */
063:
064: package org.apache.catalina.startup;
065:
066: import java.io.File;
067: import java.io.IOException;
068: import java.lang.reflect.Method;
069: import java.net.MalformedURLException;
070: import java.net.URL;
071: import java.util.ArrayList;
072: import org.apache.commons.daemon.Daemon;
073: import org.apache.commons.daemon.DaemonContext;
074: import org.apache.catalina.loader.Extension;
075: import org.apache.catalina.loader.StandardClassLoader;
076:
077: /**
078: * Special version of the Catalina bootstrap, designed to be invoked with JNI,
079: * and designed to allow easier wrapping by system level components, which
080: * would otherwise be confused by the asychronous startup and shutdown Catalina
081: * uses. This class should be used to run Catalina as a system service under
082: * Windows NT and clones.
083: *
084: * @author Craig R. McClanahan
085: * @author Remy Maucherat
086: * @version $Revision: 1.16 $ $Date: 2002/07/11 13:47:02 $
087: */
088:
089: public final class BootstrapService implements Daemon {
090:
091: // ------------------------------------------------------- Static Variables
092:
093: /**
094: * Service object used by main.
095: */
096: private static Daemon service = null;
097:
098: /**
099: * Debugging detail level for processing the startup.
100: */
101: private static int debug = 0;
102:
103: /**
104: * Catalina service.
105: */
106: private Object catalinaService = null;
107:
108: // -------------------------------------------------------- Service Methods
109:
110: /**
111: * Load the Catalina Service.
112: */
113: public void init(DaemonContext context) throws Exception {
114:
115: String arguments[] = null;
116:
117: /* Read the arguments from the Daemon context */
118: if (context != null) {
119: arguments = context.getArguments();
120: if (arguments != null) {
121: for (int i = 0; i < arguments.length; i++) {
122: if (arguments[i].equals("-debug")) {
123: debug = 1;
124: }
125: }
126: }
127: }
128:
129: log("Create Catalina server");
130:
131: // Set Catalina path
132: setCatalinaHome();
133: setCatalinaBase();
134:
135: // Construct the class loaders we will need
136: ClassLoader commonLoader = null;
137: ClassLoader catalinaLoader = null;
138: ClassLoader sharedLoader = null;
139: try {
140:
141: File unpacked[] = new File[1];
142: File packed[] = new File[1];
143: File packed2[] = new File[2];
144: ClassLoaderFactory.setDebug(debug);
145:
146: unpacked[0] = new File(getCatalinaHome(), "common"
147: + File.separator + "classes");
148: packed2[0] = new File(getCatalinaHome(), "common"
149: + File.separator + "endorsed");
150: packed2[1] = new File(getCatalinaHome(), "common"
151: + File.separator + "lib");
152: commonLoader = ClassLoaderFactory.createClassLoader(
153: unpacked, packed2, null);
154:
155: unpacked[0] = new File(getCatalinaHome(), "server"
156: + File.separator + "classes");
157: packed[0] = new File(getCatalinaHome(), "server"
158: + File.separator + "lib");
159: catalinaLoader = ClassLoaderFactory.createClassLoader(
160: unpacked, packed, commonLoader);
161:
162: unpacked[0] = new File(getCatalinaBase(), "shared"
163: + File.separator + "classes");
164: packed[0] = new File(getCatalinaBase(), "shared"
165: + File.separator + "lib");
166: sharedLoader = ClassLoaderFactory.createClassLoader(
167: unpacked, packed, commonLoader);
168:
169: } catch (Throwable t) {
170:
171: log("Class loader creation threw exception", t);
172:
173: }
174:
175: Thread.currentThread().setContextClassLoader(catalinaLoader);
176:
177: SecurityClassLoad.securityClassLoad(catalinaLoader);
178:
179: // Load our startup class and call its process() method
180: if (debug >= 1)
181: log("Loading startup class");
182: Class startupClass = catalinaLoader
183: .loadClass("org.apache.catalina.startup.CatalinaService");
184: Object startupInstance = startupClass.newInstance();
185:
186: // Set the shared extensions class loader
187: if (debug >= 1)
188: log("Setting startup class properties");
189: String methodName = "setParentClassLoader";
190: Class paramTypes[] = new Class[1];
191: paramTypes[0] = Class.forName("java.lang.ClassLoader");
192: Object paramValues[] = new Object[1];
193: paramValues[0] = sharedLoader;
194: Method method = startupInstance.getClass().getMethod(
195: methodName, paramTypes);
196: method.invoke(startupInstance, paramValues);
197:
198: catalinaService = startupInstance;
199:
200: // Call the load() method
201: methodName = "load";
202: Object param[];
203: if (arguments == null || arguments.length == 0) {
204: paramTypes = null;
205: param = null;
206: } else {
207: paramTypes[0] = arguments.getClass();
208: param = new Object[1];
209: param[0] = arguments;
210: }
211: method = catalinaService.getClass().getMethod(methodName,
212: paramTypes);
213: if (debug >= 1)
214: log("Calling startup class " + method);
215: method.invoke(catalinaService, param);
216:
217: }
218:
219: /**
220: * Start the Catalina Service.
221: */
222: public void start() throws Exception {
223:
224: log("Starting service");
225: String methodName = "start";
226: Method method = catalinaService.getClass().getMethod(
227: methodName, null);
228: method.invoke(catalinaService, null);
229: log("Service started");
230:
231: }
232:
233: /**
234: * Stop the Catalina Service.
235: */
236: public void stop() throws Exception {
237:
238: log("Stopping service");
239: String methodName = "stop";
240: Method method = catalinaService.getClass().getMethod(
241: methodName, null);
242: method.invoke(catalinaService, null);
243: log("Service stopped");
244:
245: }
246:
247: /**
248: * Destroy the Catalina Service.
249: */
250: public void destroy() {
251:
252: // FIXME
253:
254: }
255:
256: // ----------------------------------------------------------- Main Program
257:
258: /**
259: * Main method, used for testing only.
260: *
261: * @param args Command line arguments to be processed
262: */
263: public static void main(String args[]) {
264:
265: // Set the debug flag appropriately
266: for (int i = 0; i < args.length; i++) {
267: if ("-debug".equals(args[i]))
268: debug = 1;
269: }
270:
271: if (service == null) {
272: service = new BootstrapService();
273: try {
274: service.init(null);
275: } catch (Throwable t) {
276: t.printStackTrace();
277: return;
278: }
279: }
280:
281: try {
282: String command = args[0];
283: if (command.equals("start")) {
284: service.start();
285: } else if (command.equals("stop")) {
286: service.stop();
287: }
288: } catch (Throwable t) {
289: t.printStackTrace();
290: }
291:
292: }
293:
294: /**
295: * Set the <code>catalina.base</code> System property to the current
296: * working directory if it has not been set.
297: */
298: private void setCatalinaBase() {
299:
300: if (System.getProperty("catalina.base") != null)
301: return;
302: if (System.getProperty("catalina.home") != null)
303: System.setProperty("catalina.base", System
304: .getProperty("catalina.home"));
305: else
306: System.setProperty("catalina.base", System
307: .getProperty("user.dir"));
308:
309: }
310:
311: /**
312: * Set the <code>catalina.home</code> System property to the current
313: * working directory if it has not been set.
314: */
315: private void setCatalinaHome() {
316:
317: if (System.getProperty("catalina.home") != null)
318: return;
319: System.setProperty("catalina.home", System
320: .getProperty("user.dir"));
321:
322: }
323:
324: /**
325: * Get the value of the catalina.home environment variable.
326: */
327: private static String getCatalinaHome() {
328: return System.getProperty("catalina.home", System
329: .getProperty("user.dir"));
330: }
331:
332: /**
333: * Get the value of the catalina.base environment variable.
334: */
335: private static String getCatalinaBase() {
336: return System.getProperty("catalina.base", getCatalinaHome());
337: }
338:
339: /**
340: * Log a debugging detail message.
341: *
342: * @param message The message to be logged
343: */
344: private static void log(String message) {
345:
346: System.out.print("Bootstrap: ");
347: System.out.println(message);
348:
349: }
350:
351: /**
352: * Log a debugging detail message with an exception.
353: *
354: * @param message The message to be logged
355: * @param exception The exception to be logged
356: */
357: private static void log(String message, Throwable exception) {
358:
359: log(message);
360: exception.printStackTrace(System.out);
361:
362: }
363:
364: }
|