(no commit message)
[utils] / support / general / src / main / java / org / wamblee / reflection / ReflectionUtils.java
1 /*
2  * Copyright 2005-2010 the original author or authors.
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 package org.wamblee.reflection;
17
18 import java.lang.reflect.Field;
19 import java.lang.reflect.Method;
20 import java.util.ArrayList;
21 import java.util.Arrays;
22 import java.util.HashMap;
23 import java.util.List;
24 import java.util.Map;
25
26 /**
27  * Some utilities for reflection.
28  * 
29  * @author Erik Brakkee
30  */
31 public class ReflectionUtils {
32
33     public static final List<Class> PRIMITIVE_WRAPPERS = createPrimitiveWrappers();
34
35     private static final List<Class> createPrimitiveWrappers() {
36         Class[] vals = { Boolean.class, Byte.class, Character.class,
37             Short.class, Integer.class, Long.class, Float.class, Double.class };
38         return Arrays.asList(vals);
39     }
40
41     /**
42      * Wraps a type by the corresponding wrapper type if it is a primitive type.
43      * 
44      * @param aClass
45      *            Type to wrap.
46      * @return Wrapped type for primitives or the provided argument value.
47      */
48     public static Class wrapIfNeeded(Class aClass) {
49         if (aClass == boolean.class) {
50             return Boolean.class;
51         }
52
53         if (aClass == byte.class) {
54             return Byte.class;
55         }
56
57         if (aClass == char.class) {
58             return Character.class;
59         }
60
61         if (aClass == short.class) {
62             return Short.class;
63         }
64
65         if (aClass == int.class) {
66             return Integer.class;
67         }
68
69         if (aClass == long.class) {
70             return Long.class;
71         }
72
73         if (aClass == float.class) {
74             return Float.class;
75         }
76
77         if (aClass == double.class) {
78             return Double.class;
79         }
80
81         if (aClass == void.class) {
82             return Void.class;
83         }
84
85         return aClass;
86     }
87
88     public static List<Method> getAllMethods(Class aClass,
89         Class... aExcludedClasses) {
90         if (aClass.isInterface()) {
91             throw new IllegalArgumentException(aClass.getName() +
92                 " is not an interface.");
93         }
94         Map<String, Method> found = new HashMap<String, Method>();
95         getAllMethods(aClass, found, Arrays.asList(aExcludedClasses));
96
97         return new ArrayList<Method>(found.values());
98     }
99
100     private static void getAllMethods(Class aClass, Map<String, Method> aFound,
101         List<Class> aExcludedClasses) {
102         List<Method> declared = Arrays.asList(aClass.getDeclaredMethods());
103
104         for (Method method : declared) {
105             Method superMethod = aFound.get(method.getName());
106
107             if (superMethod == null) {
108                 // no subclass method
109                 aFound.put(method.getName(), method);
110             } else {
111                 // subclass method. Check for override.
112                 if (!Arrays.equals(superMethod.getParameterTypes(), method
113                     .getParameterTypes())) {
114                     // parameters differ so this is a new method.
115                     aFound.put(method.getName(), method);
116                 }
117             }
118         }
119
120         Class superClass = aClass.getSuperclass();
121
122         if (superClass != null && !aExcludedClasses.contains(superClass)) {
123             getAllMethods(superClass, aFound, aExcludedClasses);
124         }
125     }
126
127     public static List<Field> getAllFields(Class aClass,
128         Class... aExcludedClasses) {
129         if (aClass.isInterface()) {
130             throw new IllegalArgumentException(aClass.getName() +
131                 " is an interface.");
132         }
133         List<Field> found = new ArrayList<Field>();
134         getAllFields(aClass, found, Arrays.asList(aExcludedClasses));
135
136         return found;
137     }
138
139     private static void getAllFields(Class aClass, List<Field> aFound,
140         List<Class> aExcludedClasses) {
141         List<Field> declared = Arrays.asList(aClass.getDeclaredFields());
142
143         for (Field field : declared) {
144             aFound.add(field);
145         }
146
147         Class superClass = aClass.getSuperclass();
148
149         if (superClass != null && !aExcludedClasses.contains(superClass)) {
150             getAllFields(superClass, aFound, aExcludedClasses);
151         }
152     }
153
154     /**
155      * Checks if a class is a primitive type or wrapper type.
156      * 
157      * @param aClass
158      * @return
159      */
160     public static boolean isPrimitive(Class aClass) {
161         if (aClass.isPrimitive()) {
162             return true;
163         }
164         return PRIMITIVE_WRAPPERS.contains(aClass);
165     }
166 }