001: /*--
002:
003: Copyright (C) 2000-2003 Anthony Eden.
004: All rights reserved.
005:
006: Redistribution and use in source and binary forms, with or without
007: modification, are permitted provided that the following conditions
008: are met:
009:
010: 1. Redistributions of source code must retain the above copyright
011: notice, this list of conditions, and the following disclaimer.
012:
013: 2. Redistributions in binary form must reproduce the above copyright
014: notice, this list of conditions, and the disclaimer that follows
015: these conditions in the documentation and/or other materials
016: provided with the distribution.
017:
018: 3. The name "EdenLib" must not be used to endorse or promote products
019: derived from this software without prior written permission. For
020: written permission, please contact me@anthonyeden.com.
021:
022: 4. Products derived from this software may not be called "EdenLib", nor
023: may "EdenLib" appear in their name, without prior written permission
024: from Anthony Eden (me@anthonyeden.com).
025:
026: In addition, I request (but do not require) that you include in the
027: end-user documentation provided with the redistribution and/or in the
028: software itself an acknowledgement equivalent to the following:
029: "This product includes software developed by
030: Anthony Eden (http://www.anthonyeden.com/)."
031:
032: THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
033: WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
034: OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
035: DISCLAIMED. IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT,
036: INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
037: (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
038: SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
039: HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
040: STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
041: IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
042: POSSIBILITY OF SUCH DAMAGE.
043:
044: For more information on EdenLib, please see <http://edenlib.sf.net/>.
045:
046: */
047:
048: package com.anthonyeden.lib.util;
049:
050: import org.apache.commons.logging.Log;
051: import org.apache.commons.logging.LogFactory;
052:
053: import java.io.InputStream;
054: import java.net.URL;
055: import java.util.ArrayList;
056: import java.util.List;
057:
058: /**
059: * Useful class management utilities.
060: *
061: * @author Anthony Eden
062: * @author Florin PATRASCU
063: */
064:
065: public class ClassUtilities {
066:
067: private static Log log = LogFactory.getLog(ClassUtilities.class);
068:
069: /**
070: * Load the specified class name. This method will first attempt to load
071: * the class using the context class loader. If that fails due to a
072: * ClassNotFoundException or a SecurityException then the ClassUtilities
073: * class loader is used.
074: *
075: * @param className The class name
076: * @return The Class
077: * @throws ClassNotFoundException
078: */
079:
080: public static Class loadClass(String className)
081: throws ClassNotFoundException {
082: return loadClass(className, null);
083: }
084:
085: /**
086: * Load the specified class name. This method will first attempt to load
087: * the class using the context class loader. If that fails due to a
088: * ClassNotFoundException or a SecurityException then the requestor's
089: * class loader is used. If the requestor object is null then the
090: * ClassUtilities class loader is used.
091: *
092: * @param className The class name
093: * @param requestor The object requesting the class or null
094: * @return The Class
095: * @throws ClassNotFoundException
096: */
097:
098: public static Class loadClass(String className, Object requestor)
099: throws ClassNotFoundException {
100: Class requestorClass = null;
101: if (requestor == null) {
102: requestorClass = ClassUtilities.class;
103: } else {
104: requestorClass = requestor.getClass();
105: }
106: return loadClass(className, requestorClass);
107: }
108:
109: /**
110: * Load the specified class name. This method will first attempt to load
111: * the class using the context class loader. If that fails due to a
112: * ClassNotFoundException or a SecurityException then the requestor's
113: * class loader is used. If the requestor object is null then the
114: * ClassUtilities class loader is used.
115: *
116: * @param className The class name
117: * @param requestor The class of the object requesting the class or null
118: * @return The Class
119: * @throws ClassNotFoundException
120: */
121:
122: public static Class loadClass(String className, Class requestor)
123: throws ClassNotFoundException {
124: ClassLoader cl = Thread.currentThread().getContextClassLoader();
125: try {
126: return cl.loadClass(className);
127: } catch (ClassNotFoundException e) {
128: log
129: .warn(className
130: + "; ClassNotFoundException using thread context class loader");
131: cl = requestor.getClass().getClassLoader();
132: return cl.loadClass(className);
133: } catch (SecurityException e) {
134: log
135: .warn(className
136: + "; SecurityException using thread context class loader");
137: cl = requestor.getClass().getClassLoader();
138: return cl.loadClass(className);
139: }
140: }
141:
142: /**
143: * Load the specified resource. This method will first attempt to load
144: * the class using the context class loader. If that fails due to a
145: * ClassNotFoundException or a SecurityException then the ClassUtilities
146: * class loader is used.
147: *
148: * @param name The resource name
149: * @return The resource URL or null
150: */
151:
152: public static URL getResource(String name) {
153: return getResource(name, null);
154: }
155:
156: /**
157: * Load the specified resource. This method will first attempt to load
158: * the class using the context class loader. If that fails due to a
159: * ClassNotFoundException or a SecurityException then the requestor's
160: * class loader is used. If the requestor object is null then the
161: * ClassUtilities class loader is used.
162: *
163: * @param name The resource name
164: * @param requestor The object requesting the resource or null
165: * @return The resource URL or null
166: */
167:
168: public static URL getResource(String name, Object requestor) {
169: Class requestorClass = null;
170: if (requestor == null) {
171: requestorClass = ClassUtilities.class;
172: } else {
173: requestorClass = requestor.getClass();
174: }
175: return getResource(name, requestorClass);
176: }
177:
178: /**
179: * Load the specified resource. This method will first attempt to load
180: * the class using the context class loader. If that fails due to a
181: * ClassNotFoundException or a SecurityException then the requestor's
182: * class loader is used. If the requestor object is null then the
183: * ClassUtilities class loader is used.
184: *
185: * @param name The resource name
186: * @param requestor The class of the object requesting the resource or null
187: * @return The resource URL or null
188: */
189:
190: public static URL getResource(String name, Class requestor) {
191: URL resource;
192: ClassLoader cl = Thread.currentThread().getContextClassLoader();
193: resource = cl.getResource(name);
194: if (resource == null) {
195: cl = requestor.getClass().getClassLoader();
196: resource = cl.getResource(name);
197: }
198: return resource;
199: }
200:
201: /**
202: * Load the specified resource stream. This method will first attempt to
203: * load the class using the context class loader. If that fails due to a
204: * ClassNotFoundException or a SecurityException then ClassUtilities class
205: * loader is used.
206: *
207: * @param name The resource name
208: * @return The resource stream or null
209: */
210:
211: public static InputStream getResourceAsStream(String name) {
212: return getResourceAsStream(name, null);
213: }
214:
215: /**
216: * Load the specified resource stream. This method will first attempt to
217: * load the class using the context class loader. If that fails due to a
218: * ClassNotFoundException or a SecurityException then the requestor's
219: * class loader is used. If the requestor object is null then the
220: * ClassUtilities class loader is used.
221: *
222: * @param name The class name
223: * @param requestor The object requesting the resource or null
224: * @return The resource stream or null
225: */
226:
227: public static InputStream getResourceAsStream(String name,
228: Object requestor) {
229: Class requestorClass = null;
230: if (requestor == null) {
231: requestorClass = ClassUtilities.class;
232: } else {
233: requestorClass = requestor.getClass();
234: }
235: return getResourceAsStream(name, requestorClass);
236: }
237:
238: /**
239: * Load the specified resource stream. This method will first attempt to
240: * load the class using the context class loader. If that fails due to a
241: * ClassNotFoundException or a SecurityException then the requestor's
242: * class loader is used. If the requestor object is null then the
243: * ClassUtilities class loader is used.
244: *
245: * @param name The class name
246: * @param requestor The class of the object requesting the resource or null
247: * @return The resource stream or null
248: */
249:
250: public static InputStream getResourceAsStream(String name,
251: Class requestor) {
252: InputStream resourceStream = null;
253: ClassLoader cl = Thread.currentThread().getContextClassLoader();
254: resourceStream = cl.getResourceAsStream(name);
255: if (resourceStream == null) {
256: cl = requestor.getClass().getClassLoader();
257: resourceStream = cl.getResourceAsStream(name);
258: }
259: return resourceStream;
260: }
261:
262: /**
263: * Find all super classes and implemented interfaces for the given
264: * class.
265: *
266: * @param startClass The class
267: * @return A List of Class objects
268: */
269:
270: public static List getAllClassesAndInterfaces(Class startClass) {
271: ArrayList classes = new ArrayList();
272:
273: addClassesAndInterfaces(startClass, classes);
274:
275: return classes;
276: }
277:
278: /**
279: * Add all super classes and interfaces of the given class to the given
280: * List.
281: *
282: * @param c The Class
283: * @param classes An List of Classes
284: */
285:
286: protected static void addClassesAndInterfaces(Class c, List classes) {
287: if (c == null) {
288: return;
289: }
290:
291: Class super Class = c.getSuperclass();
292: Class[] interfaces = c.getInterfaces();
293:
294: if (super Class != null && !classes.contains(super Class)) {
295: //System.out.println("Adding " + superClass.getName() + " superclass of " + c.getName());
296: classes.add(super Class);
297: }
298:
299: for (int i = 0; i < interfaces.length; i++) {
300: if (interfaces[i] != null
301: && !classes.contains(interfaces[i])) {
302: //System.out.println("Adding " + interfaces[i].getName() + " interface of " + c.getName());
303: classes.add(interfaces[i]);
304: }
305: }
306:
307: addClassesAndInterfaces(super Class, classes);
308: for (int i = 0; i < interfaces.length; i++) {
309: addClassesAndInterfaces(interfaces[i], classes);
310: }
311: }
312:
313: }
|