All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.jboss.weld.environment.util.Reflections Maven / Gradle / Ivy

There is a newer version: 3.0.0.Alpha1
Show newest version
package org.jboss.weld.environment.util;

import java.lang.annotation.Annotation;
import java.lang.annotation.Inherited;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.Arrays;

import org.jboss.weld.environment.logging.CommonLogger;
import org.jboss.weld.resources.spi.ResourceLoader;
import org.jboss.weld.resources.spi.ResourceLoadingException;

public final class Reflections {

    private Reflections() {
    }

    public static boolean containsAnnotation(Class javaClass, Class requiredAnnotation) {
        for (Class clazz = javaClass; clazz != null && clazz != Object.class; clazz = clazz.getSuperclass()) {
            // class level annotations
            if (clazz == javaClass || requiredAnnotation.isAnnotationPresent(Inherited.class)) {
                if (containsAnnotations(clazz.getAnnotations(), requiredAnnotation)) {
                    return true;
                }
            }
            // fields
            for (Field field : clazz.getDeclaredFields()) {
                if (containsAnnotations(field.getAnnotations(), requiredAnnotation)) {
                    return true;
                }
            }
            // constructors
            for (Constructor constructor : clazz.getConstructors()) {
                if (containsAnnotations(constructor.getAnnotations(), requiredAnnotation)) {
                    return true;
                }
                for (Annotation[] parameterAnnotations : constructor.getParameterAnnotations()) {
                    if (containsAnnotations(parameterAnnotations, requiredAnnotation)) {
                        return true;
                    }
                }
            }
            // methods
            for (Method method : clazz.getDeclaredMethods()) {
                if (containsAnnotations(method.getAnnotations(), requiredAnnotation)) {
                    return true;
                }
                for (Annotation[] parameterAnnotations : method.getParameterAnnotations()) {
                    if (containsAnnotations(parameterAnnotations, requiredAnnotation)) {
                        return true;
                    }
                }
            }
        }
        return false;
    }

    public static  T newInstance(ResourceLoader loader, String className, Object... parameters) {
        final Class[] parameterTypes = new Class[parameters.length];
        for (int i = 0; i < parameters.length; i++) {
            parameterTypes[i] = parameters[i].getClass();
        }
        try {
            final Class clazz = cast(loader.classForName(className));
            final Constructor constructor = findConstructor(clazz, parameters);
            return constructor.newInstance(parameters);
        } catch (Exception e) {
            throw CommonLogger.LOG.unableToInstantiate(className, Arrays.toString(parameters), e);
        }
    }

    @SuppressWarnings("unchecked")
    public static  T cast(Object obj) {
        return (T) obj;
    }

    public static boolean isClassLoadable(String className, ResourceLoader resourceLoader) {
        return loadClass(className, resourceLoader) != null;
    }

    /**
     * Tries to load a class using the specified ResourceLoader. Returns null if the class is not found.
     * @param className
     * @param resourceLoader
     * @return the loaded class or null if the given class cannot be loaded
     */
    public static  Class loadClass(String className, ResourceLoader resourceLoader) {
        try {
            return cast(resourceLoader.classForName(className));
        } catch (ResourceLoadingException e) {
            return null;
        } catch (SecurityException e) {
            return null;
        }
    }

    /**
     *
     * @param annotations
     * @param metaAnnotationType
     * @return true if any of the annotations specified has the given meta annotation type specified, false
     *         otherwise
     */
    public static boolean hasBeanDefiningMetaAnnotationSpecified(Annotation[] annotations, Class metaAnnotationType) {
        for (Annotation annotation : annotations) {
            if (annotation.annotationType().isAnnotationPresent(metaAnnotationType)) {
                return true;
            }
        }
        return false;
    }

    /**
     * Does constructor lookup respecting parameter covariance.
     */
    private static  Constructor findConstructor(Class clazz, Object... parameters) {
        for (Constructor constructor : clazz.getConstructors()) {
            boolean match = true;
            for (int i = 0; i < parameters.length; i++) {
                if (!constructor.getParameterTypes()[i].isAssignableFrom(parameters[i].getClass())) {
                    match = false;
                    break;
                }
            }
            if (match) {
                return cast(constructor);
            }
        }
        throw CommonLogger.LOG.unableToFindConstructor(clazz, Arrays.toString(parameters));
    }

    private static boolean containsAnnotations(Annotation[] annotations, Class requiredAnnotation) {
        return containsAnnotation(annotations, requiredAnnotation, true);
    }

    private static boolean containsAnnotation(Annotation[] annotations, Class requiredAnnotation, boolean checkMetaAnnotations) {
        for (Annotation annotation : annotations) {
            Class annotationType = annotation.annotationType();
            if (requiredAnnotation.equals(annotationType)) {
                return true;
            }
            if (checkMetaAnnotations && containsAnnotation(annotationType.getAnnotations(), requiredAnnotation, false)) {
                return true;
            }
        }
        return false;
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy