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

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

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

import javax.lang.model.SourceVersion;

import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.regex.Pattern;

import static java.util.Arrays.stream;
import static java.util.Objects.requireNonNull;
import static java.util.stream.Collectors.joining;
import static java.util.stream.Stream.of;

public final class ClasspathSupport {

    public static final String CLASSPATH_SCHEME = "classpath";
    public static final String CLASSPATH_SCHEME_PREFIX = CLASSPATH_SCHEME + ":";
    public static final char RESOURCE_SEPARATOR_CHAR = '/';
    public static final String RESOURCE_SEPARATOR_STRING = String.valueOf(RESOURCE_SEPARATOR_CHAR);
    static final String DEFAULT_PACKAGE_NAME = "";
    private static final String CLASS_FILE_SUFFIX = ".class";
    private static final char PACKAGE_SEPARATOR_CHAR = '.';
    public static final String PACKAGE_SEPARATOR_STRING = String.valueOf(PACKAGE_SEPARATOR_CHAR);
    private static final Pattern DOT_PATTERN = Pattern.compile("\\.");

    private ClasspathSupport() {

    }

    static void requireValidPackageName(String packageName) {
        requireNonNull(packageName, "packageName must not be null");
        if (packageName.equals(DEFAULT_PACKAGE_NAME)) {
            return;
        }
        boolean valid = stream(DOT_PATTERN.split(packageName))
                .allMatch(SourceVersion::isName);
        if (!valid) {
            throw new IllegalArgumentException("Invalid part(s) in package name: " + packageName);
        }
    }

    static List getUrisForPackage(ClassLoader classLoader, String packageName) {
        return getUrisForResource(classLoader, resourceNameOfPackageName(packageName));
    }

    static List getUrisForResource(ClassLoader classLoader, String resourceName) {
        try {
            Enumeration resources = classLoader.getResources(resourceName);
            List uris = new ArrayList<>();
            while (resources.hasMoreElements()) {
                URL resource = resources.nextElement();
                uris.add(resource.toURI());
            }
            return uris;
        } catch (Exception e) {
            throw new IllegalArgumentException(e);
        }
    }

    public static String resourceNameOfPackageName(String packageName) {
        return packageName.replace(PACKAGE_SEPARATOR_CHAR, RESOURCE_SEPARATOR_CHAR);
    }

    static String determinePackageName(Path baseDir, String basePackageName, Path classFile) {
        String subPackageName = determineSubpackageName(baseDir, classFile);
        return of(basePackageName, subPackageName)
                .filter(value -> !value.isEmpty()) // default package
                .collect(joining(PACKAGE_SEPARATOR_STRING));
    }

    private static String determineSubpackageName(Path baseDir, Path resource) {
        Path relativePath = baseDir.relativize(resource.getParent());
        String pathSeparator = baseDir.getFileSystem().getSeparator();
        return relativePath.toString().replace(pathSeparator, PACKAGE_SEPARATOR_STRING);
    }

    static URI determineClasspathResourceUri(Path baseDir, String basePackagePath, Path resource) {
        String subPackageName = determineSubpackagePath(baseDir, resource);
        String resourceName = resource.getFileName().toString();
        String classpathResourcePath = of(basePackagePath, subPackageName, resourceName)
                .filter(value -> !value.isEmpty()) // default package .
                .collect(joining(RESOURCE_SEPARATOR_STRING));
        return classpathResourceUri(classpathResourcePath);
    }

    private static String determineSubpackagePath(Path baseDir, Path resource) {
        Path relativePath = baseDir.relativize(resource.getParent());
        String pathSeparator = baseDir.getFileSystem().getSeparator();
        return relativePath.toString().replace(pathSeparator, RESOURCE_SEPARATOR_STRING);
    }

    static URI classpathResourceUri(String classpathResourceName) {
        try {
            // Unlike URI.create the constructor escapes reserved characters
            return new URI(CLASSPATH_SCHEME, classpathResourceName, null);
        } catch (URISyntaxException e) {
            throw new IllegalArgumentException(e);
        }
    }

    static String determineFullyQualifiedClassName(Path baseDir, String basePackageName, Path classFile) {
        String subpackageName = determineSubpackageName(baseDir, classFile);
        String simpleClassName = determineSimpleClassName(classFile);
        return of(basePackageName, subpackageName, simpleClassName)
                .filter(value -> !value.isEmpty()) // default package
                .collect(joining(PACKAGE_SEPARATOR_STRING));
    }

    private static String determineSimpleClassName(Path classFile) {
        String fileName = classFile.getFileName().toString();
        return fileName.substring(0, fileName.length() - CLASS_FILE_SUFFIX.length());
    }

    public static String packageNameOfResource(String classpathResourceName) {
        Path parent = Paths.get(classpathResourceName).getParent();
        if (parent == null) {
            return DEFAULT_PACKAGE_NAME;
        }
        String pathSeparator = parent.getFileSystem().getSeparator();
        return parent.toString().replace(pathSeparator, PACKAGE_SEPARATOR_STRING);
    }

    static URI classpathResourceUri(Path resourcePath) {
        String pathSeparator = resourcePath.getFileSystem().getSeparator();
        String classpathResourceName = resourcePath.toString().replace(pathSeparator, RESOURCE_SEPARATOR_STRING);
        return classpathResourceUri(classpathResourceName);
    }

    public static String packageName(URI classpathResourceUri) {
        String resourceName = resourceName(classpathResourceUri);
        return resourceName.replace(RESOURCE_SEPARATOR_CHAR, PACKAGE_SEPARATOR_CHAR);
    }

    public static String resourceName(URI classpathResourceUri) {
        if (!CLASSPATH_SCHEME.equals(classpathResourceUri.getScheme())) {
            throw new IllegalArgumentException("uri must have classpath scheme " + classpathResourceUri);
        }

        String classpathResourcePath = classpathResourceUri.getSchemeSpecificPart();
        if (classpathResourcePath.startsWith(RESOURCE_SEPARATOR_STRING)) {
            return classpathResourcePath.substring(1);
        }
        return classpathResourcePath;
    }

    public static URI rootPackageUri() {
        return URI.create(CLASSPATH_SCHEME_PREFIX + RESOURCE_SEPARATOR_CHAR);
    }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy