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

io.cucumber.core.resource.ResourceScanner Maven / Gradle / Ivy

There is a newer version: 7.20.1
Show newest version
package io.cucumber.core.resource;

import java.net.URI;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Optional;
import java.util.function.BiFunction;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Predicate;
import java.util.function.Supplier;

import static io.cucumber.core.resource.ClasspathSupport.CLASSPATH_SCHEME;
import static io.cucumber.core.resource.ClasspathSupport.DEFAULT_PACKAGE_NAME;
import static io.cucumber.core.resource.ClasspathSupport.determinePackageName;
import static io.cucumber.core.resource.ClasspathSupport.getUrisForPackage;
import static io.cucumber.core.resource.ClasspathSupport.getUrisForResource;
import static io.cucumber.core.resource.ClasspathSupport.requireValidPackageName;
import static io.cucumber.core.resource.ClasspathSupport.resourceName;
import static io.cucumber.core.resource.Resources.createClasspathResource;
import static io.cucumber.core.resource.Resources.createClasspathRootResource;
import static io.cucumber.core.resource.Resources.createPackageResource;
import static io.cucumber.core.resource.Resources.createUriResource;
import static java.util.Objects.requireNonNull;
import static java.util.stream.Collectors.toList;

public final class ResourceScanner {

    private static final Predicate NULL_FILTER = x -> true;
    private final PathScanner pathScanner = new PathScanner();
    private final Supplier classLoaderSupplier;
    private final Predicate canLoad;
    private final Function> loadResource;

    public ResourceScanner(
            Supplier classLoaderSupplier,
            Predicate canLoad,
            Function> loadResource
    ) {
        this.classLoaderSupplier = classLoaderSupplier;
        this.canLoad = canLoad;
        this.loadResource = loadResource;
    }

    public List scanForResourcesInClasspathRoot(URI root, Predicate packageFilter) {
        requireNonNull(root, "root must not be null");
        requireNonNull(packageFilter, "packageFilter must not be null");
        BiFunction createResource = createClasspathRootResource();
        return findResourcesForUri(root, DEFAULT_PACKAGE_NAME, packageFilter, createResource);
    }

    private List findResourcesForUri(
            URI baseUri,
            String basePackageName,
            Predicate packageFilter,
            BiFunction createResource
    ) {
        List resources = new ArrayList<>();
        pathScanner.findResourcesForUri(
            baseUri,
            canLoad,
            processResource(basePackageName, packageFilter, createResource, resources::add));
        return resources;
    }

    private Function> processResource(
            String basePackageName,
            Predicate packageFilter,
            BiFunction createResource,
            Consumer consumer
    ) {
        return baseDir -> path -> {
            String packageName = determinePackageName(baseDir, basePackageName, path);
            if (packageFilter.test(packageName)) {
                createResource
                        .andThen(loadResource)
                        .apply(baseDir, path)
                        .ifPresent(consumer);
            }
        };
    }

    public List scanForResourcesInPackage(String packageName, Predicate packageFilter) {
        requireValidPackageName(packageName);
        requireNonNull(packageFilter, "packageFilter must not be null");
        BiFunction createResource = createPackageResource(packageName);
        List rootUrisForPackage = getUrisForPackage(getClassLoader(), packageName);
        return findResourcesForUris(rootUrisForPackage, packageName, packageFilter, createResource);
    }

    private ClassLoader getClassLoader() {
        return this.classLoaderSupplier.get();
    }

    private List findResourcesForUris(
            List baseUris,
            String basePackageName,
            Predicate packageFilter,
            BiFunction createResource
    ) {
        return baseUris.stream()
                .map(baseUri -> findResourcesForUri(baseUri, basePackageName, packageFilter, createResource))
                .flatMap(Collection::stream)
                .distinct()
                .collect(toList());
    }

    public List scanForClasspathResource(String resourceName, Predicate packageFilter) {
        requireNonNull(resourceName, "resourceName must not be null");
        requireNonNull(packageFilter, "packageFilter must not be null");
        List urisForResource = getUrisForResource(getClassLoader(), resourceName);
        BiFunction createResource = createClasspathResource(resourceName);
        return findResourcesForUris(urisForResource, DEFAULT_PACKAGE_NAME, packageFilter, createResource);
    }

    public List scanForResourcesPath(Path resourcePath) {
        requireNonNull(resourcePath, "resourcePath must not be null");
        List resources = new ArrayList<>();
        pathScanner.findResourcesForPath(
            resourcePath,
            canLoad,
            processResource(DEFAULT_PACKAGE_NAME, NULL_FILTER, createUriResource(), resources::add));
        return resources;
    }

    public List scanForResourcesUri(URI classpathResourceUri) {
        requireNonNull(classpathResourceUri, "classpathResourceUri must not be null");
        if (CLASSPATH_SCHEME.equals(classpathResourceUri.getScheme())) {
            return scanForClasspathResource(resourceName(classpathResourceUri), NULL_FILTER);
        }

        return findResourcesForUri(classpathResourceUri, DEFAULT_PACKAGE_NAME, NULL_FILTER, createUriResource());
    }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy