一、前言
基于granite源码包org.granite.util.Reflections反射映射实现类,调用invoke目标对象指定方法、获取/赋值指定目标对象指定属性java.lang.reflect.Field的值、将对象方法转为字符串toString、获取类的getter方法getGetterMethod、获取类指定属性或集合getField/getFields及类对象实例化区分isInstanceOf等操作。
二、源码说明
package org.granite.util;@b@@b@import java.beans.Introspector;@b@import java.lang.annotation.Annotation;@b@import java.lang.reflect.Field;@b@import java.lang.reflect.InvocationTargetException;@b@import java.lang.reflect.Method;@b@import java.lang.reflect.ParameterizedType;@b@import java.lang.reflect.Type;@b@import java.util.ArrayList;@b@import java.util.List;@b@@b@public class Reflections@b@{@b@ public static Object invoke(Method method, Object target, Object[] args)@b@ throws Exception@b@ {@b@ try@b@ {@b@ return method.invoke(target, args);@b@ }@b@ catch (IllegalArgumentException iae)@b@ {@b@ String message = "Could not invoke method by reflection: " + toString(method);@b@ if ((args != null) && (args.length > 0))@b@ {@b@ message = message + " with parameters: (" + Strings.toClassNameString(", ", args) + ')';@b@ }@b@ message = message + " on: " + target.getClass().getName();@b@ throw new IllegalArgumentException(message, iae);@b@ }@b@ catch (InvocationTargetException ite)@b@ {@b@ if (ite.getCause() instanceof Exception)@b@ {@b@ throw ((Exception)ite.getCause());@b@ }@b@@b@ throw ite;@b@ }@b@ }@b@@b@ public static Object get(Field field, Object target) throws Exception@b@ {@b@ try@b@ {@b@ return field.get(target);@b@ }@b@ catch (IllegalArgumentException iae)@b@ {@b@ String message = "Could not get field value by reflection: " + toString(field) + @b@ " on: " + target.getClass().getName();@b@ throw new IllegalArgumentException(message, iae);@b@ }@b@ }@b@@b@ public static void set(Field field, Object target, Object value) throws Exception@b@ {@b@ try@b@ {@b@ field.set(target, value);@b@ }@b@ catch (IllegalArgumentException iae)@b@ {@b@ String message = "Could not set field value by reflection: " + toString(field) + @b@ " on: " + field.getDeclaringClass().getName();@b@ if (value == null)@b@ {@b@ message = message + " with null value";@b@ }@b@ else@b@ {@b@ message = message + " with value: " + value.getClass();@b@ }@b@ throw new IllegalArgumentException(message, iae);@b@ }@b@ }@b@@b@ public static Object getAndWrap(Field field, Object target)@b@ {@b@ try@b@ {@b@ return get(field, target);@b@ }@b@ catch (Exception e)@b@ {@b@ if (e instanceof RuntimeException)@b@ {@b@ throw ((RuntimeException)e);@b@ }@b@@b@ throw new IllegalArgumentException("exception setting: " + field.getName(), e);@b@ }@b@ }@b@@b@ public static void setAndWrap(Field field, Object target, Object value)@b@ {@b@ try@b@ {@b@ set(field, target, value);@b@ }@b@ catch (Exception e)@b@ {@b@ if (e instanceof RuntimeException)@b@ {@b@ throw ((RuntimeException)e);@b@ }@b@@b@ throw new IllegalArgumentException("exception setting: " + field.getName(), e);@b@ }@b@ }@b@@b@ public static Object invokeAndWrap(Method method, Object target, Object[] args)@b@ {@b@ try@b@ {@b@ return invoke(method, target, args);@b@ }@b@ catch (Exception e)@b@ {@b@ if (e instanceof RuntimeException)@b@ {@b@ throw ((RuntimeException)e);@b@ }@b@@b@ throw new RuntimeException("exception invoking: " + method.getName(), e);@b@ }@b@ }@b@@b@ private static String toString(Method method)@b@ {@b@ return Strings.unqualify(method.getDeclaringClass().getName()) + @b@ '.' + @b@ method.getName() + @b@ '(' + @b@ Strings.toString(", ", method.getParameterTypes()) + @b@ ')';@b@ }@b@@b@ private static String toString(Field field)@b@ {@b@ return Strings.unqualify(field.getDeclaringClass().getName()) + @b@ '.' + @b@ field.getName();@b@ }@b@@b@ public static Class<?> classForName(String name) throws ClassNotFoundException@b@ {@b@ try@b@ {@b@ return Thread.currentThread().getContextClassLoader().loadClass(name);@b@ }@b@ catch (Exception e) {@b@ }@b@ return Class.forName(name);@b@ }@b@@b@ public static boolean isClassAvailable(String name)@b@ {@b@ try@b@ {@b@ classForName(name);@b@ }@b@ catch (ClassNotFoundException e) {@b@ return false;@b@ }@b@ return true;@b@ }@b@@b@ public static Class<?> getCollectionElementType(Type collectionType)@b@ {@b@ if (!(collectionType instanceof ParameterizedType))@b@ {@b@ throw new IllegalArgumentException("collection type not parameterized");@b@ }@b@ Type[] typeArguments = ((ParameterizedType)collectionType).getActualTypeArguments();@b@ if (typeArguments.length == 0)@b@ {@b@ throw new IllegalArgumentException("no type arguments for collection type");@b@ }@b@ Type typeArgument = (typeArguments.length == 1) ? typeArguments[0] : typeArguments[1];@b@ if (!(typeArgument instanceof Class))@b@ {@b@ throw new IllegalArgumentException("type argument not a class");@b@ }@b@ return ((Class)typeArgument);@b@ }@b@@b@ public static Class<?> getMapKeyType(Type collectionType)@b@ {@b@ if (!(collectionType instanceof ParameterizedType))@b@ {@b@ throw new IllegalArgumentException("collection type not parameterized");@b@ }@b@ Type[] typeArguments = ((ParameterizedType)collectionType).getActualTypeArguments();@b@ if (typeArguments.length == 0)@b@ {@b@ throw new IllegalArgumentException("no type arguments for collection type");@b@ }@b@ Type typeArgument = typeArguments[0];@b@ if (!(typeArgument instanceof Class))@b@ {@b@ throw new IllegalArgumentException("type argument not a class");@b@ }@b@ return ((Class)typeArgument);@b@ }@b@@b@ public static Method getSetterMethod(Class<?> clazz, String name)@b@ {@b@ Method[] methods = clazz.getMethods();@b@ for (Method method : methods)@b@ {@b@ String methodName = method.getName();@b@ if ((methodName.startsWith("set")) && (method.getParameterTypes().length == 1) && @b@ (Introspector.decapitalize(methodName.substring(3)).equals(name)))@b@ {@b@ return method;@b@ }@b@ }@b@@b@ throw new IllegalArgumentException("no such setter method: " + clazz.getName() + '.' + name);@b@ }@b@@b@ public static Method getGetterMethod(Class<?> clazz, String name) {@b@ Method[] methods = clazz.getMethods();@b@ for (Method method : methods) {@b@ String methodName = method.getName();@b@ if ((methodName.matches("^(get|is).*")) && (method.getParameterTypes().length == 0)) {@b@ int idx = (methodName.startsWith("get")) ? 3 : 2;@b@ if (Introspector.decapitalize(methodName.substring(idx)).equals(name))@b@ return method;@b@ }@b@ }@b@ throw new IllegalArgumentException("no such getter method: " + clazz.getName() + '.' + name);@b@ }@b@@b@ public static List<Method> getGetterMethods(Class<?> clazz, Class<? extends Annotation> annotation)@b@ {@b@ List methods = new ArrayList();@b@ for (Method method : clazz.getMethods())@b@ {@b@ if (method.isAnnotationPresent(annotation))@b@ {@b@ methods.add(method);@b@ }@b@ }@b@ return methods;@b@ }@b@@b@ public static Field getField(Class<?> clazz, String name)@b@ {@b@ Class superClass = clazz;@b@ try@b@ {@b@ return superClass.getDeclaredField(name);@b@ }@b@ catch (NoSuchFieldException localNoSuchFieldException)@b@ {@b@ do@b@ superClass = superClass.getSuperclass(); while (superClass != Object.class);@b@@b@ throw new IllegalArgumentException("no such field: " + clazz.getName() + '.' + name);@b@ }@b@ }@b@@b@ public static List<Field> getFields(Class<?> clazz, Class<? extends Annotation> annotation)@b@ {@b@ List fields = new ArrayList();@b@ for (Class superClass = clazz; superClass != Object.class; superClass = superClass.getSuperclass())@b@ {@b@ for (Field field : superClass.getDeclaredFields())@b@ {@b@ if (field.isAnnotationPresent(annotation))@b@ {@b@ fields.add(field);@b@ }@b@ }@b@ }@b@ return fields;@b@ }@b@@b@ public static Method getMethod(Annotation annotation, String name)@b@ {@b@ try@b@ {@b@ return annotation.annotationType().getMethod(name, new Class[0]);@b@ }@b@ catch (NoSuchMethodException nsme) {@b@ }@b@ return null;@b@ }@b@@b@ public static boolean isInstanceOf(Class<?> clazz, String name)@b@ {@b@ Class[] arrayOfClass;@b@ if (name == null)@b@ {@b@ throw new IllegalArgumentException("name cannot be null");@b@ }@b@ for (Class c = clazz; c != Object.class; c = c.getSuperclass())@b@ {@b@ if (name.equals(c.getName()))@b@ {@b@ return true;@b@ }@b@ }@b@ int j = (arrayOfClass = clazz.getInterfaces()).length; for (int i = 0; i < j; ++i) { c = arrayOfClass[i];@b@@b@ if (name.equals(c.getName()))@b@ {@b@ return true;@b@ }@b@ }@b@ return false;@b@ }@b@}