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

cucumber.runtime.io.ClasspathResourceLoader Maven / Gradle / Ivy

There is a newer version: 1.2.6
Show newest version
package cucumber.runtime.io;

import cucumber.runtime.CucumberException;
import cucumber.runtime.Utils;

import java.io.File;
import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationTargetException;
import java.util.Collection;
import java.util.HashSet;

public class ClasspathResourceLoader implements ResourceLoader {
    private final ClassLoader classLoader;

    public ClasspathResourceLoader(ClassLoader classLoader) {
        this.classLoader = classLoader;
    }

    @Override
    public Iterable resources(String path, String suffix) {
        return new ClasspathIterable(classLoader, path, suffix);
    }

    public Collection> getAnnotations(String packageName) {
        return getDescendants(Annotation.class, packageName);
    }

    public  Collection> getDescendants(Class parentType, String packageName) {
        String packagePath = packageName.replace('.', '/').replace(File.separatorChar, '/');
        Collection> result = new HashSet>();
        for (Resource classResource : resources(packagePath, ".class")) {
            String className = classResource.getClassName();
            Class clazz = loadClass(className, classLoader);
            if (clazz != null && !parentType.equals(clazz) && parentType.isAssignableFrom(clazz)) {
                result.add(clazz.asSubclass(parentType));
            }
        }
        return result;
    }

    public  T instantiateExactlyOneSubclass(Class parentType, String packageName, Class[] constructorParams, Object[] constructorArgs) {
        Collection instances = instantiateSubclasses(parentType, packageName, constructorParams, constructorArgs);
        if (instances.size() == 1) {
            return instances.iterator().next();
        } else if (instances.size() == 0) {
            throw new CucumberException("Couldn't find a single implementation of " + parentType);
        } else {
            throw new CucumberException("Expected only one instance, but found too many: " + instances);
        }
    }

    public  Collection instantiateSubclasses(Class parentType, String packageName, Class[] constructorParams, Object[] constructorArgs) {
        Collection result = new HashSet();
        for (Class clazz : getDescendants(parentType, packageName)) {
            if (Utils.isInstantiable(clazz) && Utils.hasConstructor(clazz, constructorParams)) {
                result.add(newInstance(constructorParams, constructorArgs, clazz));
            }
        }
        return result;
    }

    private Class loadClass(String className, ClassLoader classLoader) {
        try {
            return classLoader.loadClass(className);
        } catch (ClassNotFoundException ignore) {
            return null;
        } catch (NoClassDefFoundError ignore) {
            return null;
        }
    }

    private  T newInstance(Class[] constructorParams, Object[] constructorArgs, Class clazz) {
        try {
            return clazz.getConstructor(constructorParams).newInstance(constructorArgs);
        } catch (InstantiationException e) {
            throw new CucumberException(e);
        } catch (IllegalAccessException e) {
            throw new CucumberException(e);
        } catch (InvocationTargetException e) {
            throw new CucumberException(e);
        } catch (NoSuchMethodException e) {
            throw new CucumberException(e);
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy