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

cucumber.runtime.java.ClasspathMethodScanner Maven / Gradle / Ivy

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

import cucumber.annotation.After;
import cucumber.annotation.Before;
import cucumber.annotation.Order;
import cucumber.io.ClasspathResourceLoader;
import cucumber.runtime.CucumberException;
import cucumber.runtime.Utils;

import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.List;

class ClasspathMethodScanner {

    private final ClasspathResourceLoader resourceLoader;
    private final Collection> cucumberAnnotationClasses;

    public ClasspathMethodScanner(ClasspathResourceLoader resourceLoader) {
        this.resourceLoader = resourceLoader;
        cucumberAnnotationClasses = findCucumberAnnotationClasses();
    }

    /**
     * Registers step definitions and hooks.
     *
     * @param javaBackend the backend where stepdefs and hooks will be registered
     * @param gluePaths   where to look
     */
    public void scan(JavaBackend javaBackend, List gluePaths) {
        for (String gluePath : gluePaths) {
            if(gluePath.contains("/") || gluePath.contains("\\")) {
                throw new CucumberException("Java glue must be a Java package name - not a path: " + gluePath);
            }
            // We can be fairly confident that gluePath is a packageName at this point
            for (Class glueCodeClass : resourceLoader.getDescendants(Object.class, gluePath)) {
                while (glueCodeClass != null && glueCodeClass != Object.class && !Utils.isInstantiable(glueCodeClass)) {
                    // those can't be instantiated without container class present.
                    glueCodeClass = glueCodeClass.getSuperclass();
                }
                if (glueCodeClass != null) {
                    for (Method method : glueCodeClass.getMethods()) {
                        scan(javaBackend, method);
                    }
                }
            }
        }
    }

    /**
     * Registers step definitions and hooks.
     *
     * @param javaBackend the backend where stepdefs and hooks will be registered
     * @param method      a candidate for being a stepdef or hook
     */
    public void scan(JavaBackend javaBackend, Method method) {
        for (Class cucumberAnnotationClass : cucumberAnnotationClasses) {
            Annotation annotation = method.getAnnotation(cucumberAnnotationClass);
            if (annotation != null && !annotation.annotationType().equals(Order.class)) {
                if (isHookAnnotation(annotation)) {
                    javaBackend.addHook(annotation, method);
                } else if (isStepdefAnnotation(annotation)) {
                    javaBackend.addStepDefinition(annotation, method);
                }
            }
        }
    }

    private Collection> findCucumberAnnotationClasses() {
        return resourceLoader.getAnnotations("cucumber.annotation");
    }

    private boolean isHookAnnotation(Annotation annotation) {
        Class annotationClass = annotation.annotationType();
        return annotationClass.equals(Before.class) || annotationClass.equals(After.class);
    }

    private boolean isStepdefAnnotation(Annotation annotation) {
        Class annotationClass = annotation.annotationType();
        return annotationClass.getAnnotation(StepDefAnnotation.class) != null;
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy