001
014
015 package com.liferay.portal.kernel.util;
016
017 import java.lang.reflect.Field;
018 import java.lang.reflect.Method;
019 import java.lang.reflect.Modifier;
020 import java.lang.reflect.ParameterizedType;
021 import java.lang.reflect.Type;
022
023 import java.util.Arrays;
024 import java.util.HashSet;
025 import java.util.LinkedHashSet;
026 import java.util.Set;
027
028
033 public class ReflectionUtil {
034
035 public static Object arrayClone(Object array) {
036 Class<?> clazz = array.getClass();
037
038 if (!clazz.isArray()) {
039 throw new IllegalArgumentException(
040 "Input object is not an array: " + array);
041 }
042
043 try {
044 return _CLONE_METHOD.invoke(array);
045 }
046 catch (Exception e) {
047 return throwException(e);
048 }
049 }
050
051 public static Field getDeclaredField(Class<?> clazz, String name)
052 throws Exception {
053
054 Field field = clazz.getDeclaredField(name);
055
056 if (!field.isAccessible()) {
057 field.setAccessible(true);
058 }
059
060 return unfinalField(field);
061 }
062
063 public static Method getDeclaredMethod(
064 Class<?> clazz, String name, Class<?> ... parameterTypes)
065 throws Exception {
066
067 Method method = clazz.getDeclaredMethod(name, parameterTypes);
068
069 if (!method.isAccessible()) {
070 method.setAccessible(true);
071 }
072
073 return method;
074 }
075
076 public static Type getGenericInterface(
077 Object object, Class<?> interfaceClass) {
078
079 Class<?> clazz = object.getClass();
080
081 Type genericInterface = _getGenericInterface(clazz, interfaceClass);
082
083 if (genericInterface != null) {
084 return genericInterface;
085 }
086
087 Class<?> superClass = clazz.getSuperclass();
088
089 while (superClass != null) {
090 genericInterface = _getGenericInterface(superClass, interfaceClass);
091
092 if (genericInterface != null) {
093 return genericInterface;
094 }
095
096 superClass = superClass.getSuperclass();
097 }
098
099 return null;
100 }
101
102 public static Class<?> getGenericSuperType(Class<?> clazz) {
103 try {
104 ParameterizedType parameterizedType =
105 (ParameterizedType)clazz.getGenericSuperclass();
106
107 Type[] types = parameterizedType.getActualTypeArguments();
108
109 if (types.length > 0) {
110 return (Class<?>)types[0];
111 }
112 }
113 catch (Throwable t) {
114 }
115
116 return null;
117 }
118
119 public static Class<?>[] getInterfaces(Object object) {
120 return getInterfaces(object, null);
121 }
122
123 public static Class<?>[] getInterfaces(
124 Object object, ClassLoader classLoader) {
125
126 Set<Class<?>> interfaceClasses = new LinkedHashSet<>();
127
128 Class<?> clazz = object.getClass();
129
130 _getInterfaces(interfaceClasses, clazz, classLoader);
131
132 Class<?> superClass = clazz.getSuperclass();
133
134 while (superClass != null) {
135 _getInterfaces(interfaceClasses, superClass, classLoader);
136
137 superClass = superClass.getSuperclass();
138 }
139
140 return interfaceClasses.toArray(new Class<?>[interfaceClasses.size()]);
141 }
142
143 public static Class<?>[] getParameterTypes(Object[] arguments) {
144 if (arguments == null) {
145 return null;
146 }
147
148 Class<?>[] parameterTypes = new Class<?>[arguments.length];
149
150 for (int i = 0; i < arguments.length; i++) {
151 if (arguments[i] == null) {
152 parameterTypes[i] = null;
153 }
154 else if (arguments[i] instanceof Boolean) {
155 parameterTypes[i] = Boolean.TYPE;
156 }
157 else if (arguments[i] instanceof Byte) {
158 parameterTypes[i] = Byte.TYPE;
159 }
160 else if (arguments[i] instanceof Character) {
161 parameterTypes[i] = Character.TYPE;
162 }
163 else if (arguments[i] instanceof Double) {
164 parameterTypes[i] = Double.TYPE;
165 }
166 else if (arguments[i] instanceof Float) {
167 parameterTypes[i] = Float.TYPE;
168 }
169 else if (arguments[i] instanceof Integer) {
170 parameterTypes[i] = Integer.TYPE;
171 }
172 else if (arguments[i] instanceof Long) {
173 parameterTypes[i] = Long.TYPE;
174 }
175 else if (arguments[i] instanceof Short) {
176 parameterTypes[i] = Short.TYPE;
177 }
178 else {
179 parameterTypes[i] = arguments[i].getClass();
180 }
181 }
182
183 return parameterTypes;
184 }
185
186 public static Set<Method> getVisibleMethods(Class<?> clazz) {
187 Set<Method> visibleMethods = new HashSet<>(
188 Arrays.asList(clazz.getMethods()));
189
190 visibleMethods.addAll(Arrays.asList(clazz.getDeclaredMethods()));
191
192 while ((clazz = clazz.getSuperclass()) != null) {
193 for (Method method : clazz.getDeclaredMethods()) {
194 int modifiers = method.getModifiers();
195
196 if (!Modifier.isPrivate(modifiers) &
197 !Modifier.isPublic(modifiers)) {
198
199 visibleMethods.add(method);
200 }
201 }
202 }
203
204 return visibleMethods;
205 }
206
207 public static <T> T throwException(Throwable throwable) {
208 return ReflectionUtil.<T, RuntimeException>_doThrowException(throwable);
209 }
210
211 public static Field unfinalField(Field field) throws Exception {
212 int modifiers = field.getModifiers();
213
214 if ((modifiers & Modifier.FINAL) == Modifier.FINAL) {
215 Field modifiersField = getDeclaredField(Field.class, "modifiers");
216
217 modifiersField.setInt(field, modifiers & ~Modifier.FINAL);
218 }
219
220 return field;
221 }
222
223 @SuppressWarnings("unchecked")
224 private static <T, E extends Throwable> T _doThrowException(
225 Throwable throwable)
226 throws E {
227
228 throw (E)throwable;
229 }
230
231 private static Type _getGenericInterface(
232 Class<?> clazz, Class<?> interfaceClass) {
233
234 Type[] genericInterfaces = clazz.getGenericInterfaces();
235
236 for (Type genericInterface : genericInterfaces) {
237 if (!(genericInterface instanceof ParameterizedType)) {
238 continue;
239 }
240
241 ParameterizedType parameterizedType =
242 (ParameterizedType)genericInterface;
243
244 Type rawType = parameterizedType.getRawType();
245
246 if (rawType.equals(interfaceClass)) {
247 return parameterizedType;
248 }
249 }
250
251 return null;
252 }
253
254 private static void _getInterfaces(
255 Set<Class<?>> interfaceClasses, Class<?> clazz,
256 ClassLoader classLoader) {
257
258 for (Class<?> interfaceClass : clazz.getInterfaces()) {
259 try {
260 if (classLoader != null) {
261 interfaceClasses.add(
262 classLoader.loadClass(interfaceClass.getName()));
263 }
264 else {
265 interfaceClasses.add(interfaceClass);
266 }
267 }
268 catch (ClassNotFoundException cnfe) {
269 }
270 }
271 }
272
273 private static final Method _CLONE_METHOD;
274
275 static {
276 try {
277 _CLONE_METHOD = getDeclaredMethod(Object.class, "clone");
278 }
279 catch (Exception e) {
280 throw new ExceptionInInitializerError(e);
281 }
282 }
283
284 }