KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > mule > util > ClassUtils


1 /*
2  * $Id: ClassUtils.java 3798 2006-11-04 04:07:14Z aperepel $
3  * --------------------------------------------------------------------------------------
4  * Copyright (c) MuleSource, Inc. All rights reserved. http://www.mulesource.com
5  *
6  * The software in this package is published under the terms of the MuleSource MPL
7  * license, a copy of which has been included with this distribution in the
8  * LICENSE.txt file.
9  */

10
11 package org.mule.util;
12
13 import java.io.IOException JavaDoc;
14 import java.lang.reflect.Constructor JavaDoc;
15 import java.lang.reflect.InvocationTargetException JavaDoc;
16 import java.lang.reflect.Method JavaDoc;
17 import java.lang.reflect.Modifier JavaDoc;
18 import java.net.URL JavaDoc;
19 import java.security.AccessController JavaDoc;
20 import java.security.PrivilegedAction JavaDoc;
21 import java.util.ArrayList JavaDoc;
22 import java.util.Arrays JavaDoc;
23 import java.util.Collections JavaDoc;
24 import java.util.Enumeration JavaDoc;
25 import java.util.Iterator JavaDoc;
26 import java.util.List JavaDoc;
27
28 /**
29  * This class is useful for loading resources and classes in a fault tolerant manner
30  * that works across different applications servers. The resource and classloading
31  * methods are SecurityManager friendly.
32  */

33 // @ThreadSafe
34
public class ClassUtils extends org.apache.commons.lang.ClassUtils
35 {
36     public static final Object JavaDoc[] NO_ARGS = new Object JavaDoc[]{};
37
38     public static boolean isConcrete(Class JavaDoc clazz)
39     {
40         if (clazz == null)
41         {
42             throw new NullPointerException JavaDoc("clazz");
43         }
44         return !(clazz.isInterface() || Modifier.isAbstract(clazz.getModifiers()));
45     }
46
47     /**
48      * Load a given resource. <p/> This method will try to load the resource using
49      * the following methods (in order):
50      * <ul>
51      * <li>From
52      * {@link Thread#getContextClassLoader() Thread.currentThread().getContextClassLoader()}
53      * <li>From
54      * {@link Class#getClassLoader() ClassLoaderUtil.class.getClassLoader()}
55      * <li>From the {@link Class#getClassLoader() callingClass.getClassLoader() }
56      * </ul>
57      *
58      * @param resourceName The name of the resource to load
59      * @param callingClass The Class object of the calling object
60      */

61     public static URL JavaDoc getResource(final String JavaDoc resourceName, final Class JavaDoc callingClass)
62     {
63         URL JavaDoc url = (URL JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
64         {
65             public Object JavaDoc run()
66             {
67                 return Thread.currentThread().getContextClassLoader().getResource(resourceName);
68             }
69         });
70
71         if (url == null)
72         {
73             url = (URL JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
74             {
75                 public Object JavaDoc run()
76                 {
77                     return ClassUtils.class.getClassLoader().getResource(resourceName);
78                 }
79             });
80         }
81
82         if (url == null)
83         {
84             url = (URL JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
85             {
86                 public Object JavaDoc run()
87                 {
88                     return callingClass.getClassLoader().getResource(resourceName);
89                 }
90             });
91         }
92
93         return url;
94     }
95
96     public static Enumeration JavaDoc getResources(final String JavaDoc resourceName, final Class JavaDoc callingClass)
97     {
98         Enumeration JavaDoc enumeration = (Enumeration JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
99         {
100             public Object JavaDoc run()
101             {
102                 try
103                 {
104                     return Thread.currentThread().getContextClassLoader().getResources(resourceName);
105                 }
106                 catch (IOException JavaDoc e)
107                 {
108                     return null;
109                 }
110             }
111         });
112
113         if (enumeration == null)
114         {
115             enumeration = (Enumeration JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
116             {
117                 public Object JavaDoc run()
118                 {
119                     try
120                     {
121                         return ClassUtils.class.getClassLoader().getResources(resourceName);
122                     }
123                     catch (IOException JavaDoc e)
124                     {
125                         return null;
126                     }
127                 }
128             });
129         }
130
131         if (enumeration == null)
132         {
133             enumeration = (Enumeration JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
134             {
135                 public Object JavaDoc run()
136                 {
137                     try
138                     {
139                         return callingClass.getClassLoader().getResources(resourceName);
140                     }
141                     catch (IOException JavaDoc e)
142                     {
143                         return null;
144                     }
145                 }
146             });
147         }
148
149         return enumeration;
150     }
151
152     /**
153      * Load a class with a given name. <p/> It will try to load the class in the
154      * following order:
155      * <ul>
156      * <li>From
157      * {@link Thread#getContextClassLoader() Thread.currentThread().getContextClassLoader()}
158      * <li>Using the basic {@link Class#forName(java.lang.String) }
159      * <li>From
160      * {@link Class#getClassLoader() ClassLoaderUtil.class.getClassLoader()}
161      * <li>From the {@link Class#getClassLoader() callingClass.getClassLoader() }
162      * </ul>
163      *
164      * @param className The name of the class to load
165      * @param callingClass The Class object of the calling object
166      * @throws ClassNotFoundException If the class cannot be found anywhere.
167      */

168     public static Class JavaDoc loadClass(final String JavaDoc className, final Class JavaDoc callingClass)
169         throws ClassNotFoundException JavaDoc
170     {
171         Class JavaDoc clazz = (Class JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
172         {
173             public Object JavaDoc run()
174             {
175                 try
176                 {
177                     return Thread.currentThread().getContextClassLoader().loadClass(className);
178                 }
179                 catch (ClassNotFoundException JavaDoc e)
180                 {
181                     return null;
182                 }
183             }
184         });
185
186         if (clazz == null)
187         {
188             clazz = (Class JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
189             {
190                 public Object JavaDoc run()
191                 {
192                     try
193                     {
194                         return Class.forName(className);
195                     }
196                     catch (ClassNotFoundException JavaDoc e)
197                     {
198                         return null;
199                     }
200                 }
201             });
202         }
203
204         if (clazz == null)
205         {
206             clazz = (Class JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
207             {
208                 public Object JavaDoc run()
209                 {
210                     try
211                     {
212                         return ClassUtils.class.getClassLoader().loadClass(className);
213                     }
214                     catch (ClassNotFoundException JavaDoc e)
215                     {
216                         return null;
217                     }
218                 }
219             });
220         }
221
222         if (clazz == null)
223         {
224             clazz = (Class JavaDoc)AccessController.doPrivileged(new PrivilegedAction JavaDoc()
225             {
226                 public Object JavaDoc run()
227                 {
228                     try
229                     {
230                         return callingClass.getClassLoader().loadClass(className);
231                     }
232                     catch (ClassNotFoundException JavaDoc e)
233                     {
234                         return null;
235                     }
236                 }
237             });
238         }
239
240         if (clazz == null)
241         {
242             throw new ClassNotFoundException JavaDoc(className);
243         }
244
245         return clazz;
246     }
247
248     /**
249      * Prints the current classloader hierarchy - useful for debugging.
250      */

251     public static void printClassLoader()
252     {
253         System.out.println("ClassLoaderUtils.printClassLoader");
254         printClassLoader(Thread.currentThread().getContextClassLoader());
255     }
256
257     /**
258      * Prints the classloader hierarchy from a given classloader - useful for
259      * debugging.
260      */

261     public static void printClassLoader(ClassLoader JavaDoc cl)
262     {
263         System.out.println("ClassLoaderUtils.printClassLoader(cl = " + cl + ")");
264
265         if (cl != null)
266         {
267             printClassLoader(cl.getParent());
268         }
269     }
270
271     public static Object JavaDoc instanciateClass(Class JavaDoc clazz, Object JavaDoc[] constructorArgs)
272         throws SecurityException JavaDoc, NoSuchMethodException JavaDoc, IllegalArgumentException JavaDoc, InstantiationException JavaDoc,
273         IllegalAccessException JavaDoc, InvocationTargetException JavaDoc
274     {
275         Class JavaDoc[] args;
276         if (constructorArgs != null)
277         {
278             args = new Class JavaDoc[constructorArgs.length];
279             for (int i = 0; i < constructorArgs.length; i++)
280             {
281                 if (constructorArgs[i] == null)
282                 {
283                     args[i] = null;
284                 }
285                 else
286                 {
287                     args[i] = constructorArgs[i].getClass();
288                 }
289             }
290         }
291         else
292         {
293             args = new Class JavaDoc[0];
294         }
295         Constructor JavaDoc ctor = getConstructor(clazz, args);
296         if (ctor == null)
297         {
298             StringBuffer JavaDoc argsString = new StringBuffer JavaDoc(100);
299             for (int i = 0; i < args.length; i++)
300             {
301                 argsString.append(args[i].getName()).append(", ");
302             }
303             throw new NoSuchMethodException JavaDoc("could not find constructor with matching arg params: "
304                                             + argsString);
305         }
306
307         return ctor.newInstance(constructorArgs);
308     }
309
310     public static Object JavaDoc instanciateClass(String JavaDoc name, Object JavaDoc[] constructorArgs)
311         throws ClassNotFoundException JavaDoc, SecurityException JavaDoc, NoSuchMethodException JavaDoc, IllegalArgumentException JavaDoc,
312         InstantiationException JavaDoc, IllegalAccessException JavaDoc, InvocationTargetException JavaDoc
313     {
314         Class JavaDoc clazz = loadClass(name, ClassUtils.class);
315         return instanciateClass(clazz, constructorArgs);
316
317     }
318
319     public static Object JavaDoc instanciateClass(String JavaDoc name, Object JavaDoc[] constructorArgs, Class JavaDoc callingClass)
320         throws ClassNotFoundException JavaDoc, SecurityException JavaDoc, NoSuchMethodException JavaDoc, IllegalArgumentException JavaDoc,
321         InstantiationException JavaDoc, IllegalAccessException JavaDoc, InvocationTargetException JavaDoc
322     {
323         Class JavaDoc clazz = loadClass(name, callingClass);
324         return instanciateClass(clazz, constructorArgs);
325
326     }
327
328     public static Class JavaDoc[] getParameterTypes(Object JavaDoc bean, String JavaDoc methodName)
329     {
330         if (!methodName.startsWith("set"))
331         {
332             methodName = "set" + methodName.substring(0, 1).toUpperCase() + methodName.substring(1);
333         }
334         Method JavaDoc methods[] = bean.getClass().getMethods();
335
336         for (int i = 0; i < methods.length; i++)
337         {
338             if (methods[i].getName().equals(methodName))
339             {
340                 return methods[i].getParameterTypes();
341             }
342         }
343         return new Class JavaDoc[]{};
344     }
345
346     /**
347      * Returns a matching method for the given name and parameters on the given class
348      * If the parameterTypes arguments is null it will return the first matching
349      * method on the class
350      *
351      * @param name the method name to find
352      * @param parameterTypes an array of argument types or null
353      * @param clazz the class to find the method on
354      * @return the Method object or null if none was found
355      */

356     public static Method JavaDoc getMethod(String JavaDoc name, Class JavaDoc[] parameterTypes, Class JavaDoc clazz)
357     {
358         Method JavaDoc[] methods = clazz.getMethods();
359         for (int i = 0; i < methods.length; i++)
360         {
361             if (methods[i].getName().equals(name))
362             {
363                 if (parameterTypes == null)
364                 {
365                     return methods[i];
366                 }
367                 else if (Arrays.equals(methods[i].getParameterTypes(), parameterTypes))
368                 {
369                     return methods[i];
370                 }
371             }
372         }
373         return null;
374     }
375
376     public static Constructor JavaDoc getConstructor(Class JavaDoc clazz, Class JavaDoc[] paramTypes)
377     {
378         Constructor JavaDoc[] ctors = clazz.getConstructors();
379         for (int i = 0; i < ctors.length; i++)
380         {
381             if (ctors[i].getParameterTypes().length == paramTypes.length)
382             {
383                 Class JavaDoc[] types = ctors[i].getParameterTypes();
384                 boolean match = true;
385                 for (int x = 0; x < types.length; x++)
386                 {
387                     if (paramTypes[x] == null)
388                     {
389                         match = true;
390                     }
391                     else
392                     {
393                         match = types[x].isAssignableFrom(paramTypes[x]);
394                     }
395                 }
396                 if (match)
397                 {
398                     return ctors[i];
399                 }
400             }
401         }
402         return null;
403     }
404
405     /**
406      * A helper method that will find all matching methods on a class with the given
407      * parameter type
408      *
409      * @param implementation the class to build methods on
410      * @param parameterTypes the argument param types to look for
411      * @param voidOk whether void methods shouldbe included in the found list
412      * @param matchOnObject Determines whether parameters of OBject type are matched
413      * when they are of Object.class type
414      * @param ignoreMethods An array of method names to ignore. Often 'equals' is not
415      * a desired match. This argument can be null.
416      * @return a list of methods on the class that match the criteria. If there are
417      * none, an empty list is returned
418      */

419     public static List JavaDoc getSatisfiableMethods(Class JavaDoc implementation,
420                                              Class JavaDoc[] parameterTypes,
421                                              boolean voidOk,
422                                              boolean matchOnObject,
423                                              String JavaDoc[] ignoreMethods)
424     {
425         List JavaDoc result = new ArrayList JavaDoc();
426         List JavaDoc ignore = (ignoreMethods == null ? Collections.EMPTY_LIST : Arrays.asList(ignoreMethods));
427         List JavaDoc methods = Arrays.asList(implementation.getMethods());
428         for (Iterator JavaDoc iterator = methods.iterator(); iterator.hasNext();)
429         {
430             Method JavaDoc method = (Method JavaDoc)iterator.next();
431             Class JavaDoc[] methodParams = method.getParameterTypes();
432
433             if (compare(methodParams, parameterTypes, matchOnObject))
434             {
435                 if (!ignore.contains(method.getName()))
436                 {
437                     if ((method.getReturnType().getName().equals("void") && voidOk)
438                         || !method.getReturnType().getName().equals("void"))
439                     {
440                         result.add(method);
441                     }
442                 }
443             }
444         }
445         return result;
446     }
447
448     /**
449      * Can be used by serice endpoints to select which service to use based on what's
450      * loaded on the classpath
451      *
452      * @param className The class name to look for
453      * @param currentClass the calling class
454      * @return true if the class is on the path
455      */

456     public static boolean isClassOnPath(String JavaDoc className, Class JavaDoc currentClass)
457     {
458         try
459         {
460             return (loadClass(className, currentClass) != null);
461         }
462         catch (ClassNotFoundException JavaDoc e)
463         {
464             return false;
465         }
466     }
467
468     /**
469      * Used for creating an array of class types for an array or single object
470      *
471      * @param object single object or array
472      * @return an array of class types for the object
473      */

474     public static Class JavaDoc[] getClassTypes(Object JavaDoc object)
475     {
476         Class JavaDoc[] types;
477         if (object instanceof Object JavaDoc[])
478         {
479             Object JavaDoc[] objects = (Object JavaDoc[])object;
480             types = new Class JavaDoc[objects.length];
481             for (int i = 0; i < objects.length; i++)
482             {
483                 types[i] = objects[i].getClass();
484             }
485         }
486         else
487         {
488             types = new Class JavaDoc[1];
489             types[0] = object.getClass();
490         }
491         return types;
492     }
493
494     public static String JavaDoc getClassName(Class JavaDoc clazz)
495     {
496         if (clazz == null)
497         {
498             return null;
499         }
500         String JavaDoc name = clazz.getName();
501         return name.substring(name.lastIndexOf(".") + 1);
502     }
503
504     public static boolean compare(Class JavaDoc[] c1, Class JavaDoc[] c2, boolean matchOnObject)
505     {
506         if (c1.length != c2.length)
507         {
508             return false;
509         }
510         for (int i = 0; i < c1.length; i++)
511         {
512             if (c1[i].equals(Object JavaDoc.class) && !matchOnObject)
513             {
514                 return false;
515             }
516             if (!c1[i].isAssignableFrom(c2[i]))
517             {
518
519                 return false;
520             }
521         }
522         return true;
523     }
524 }
525
Popular Tags