From ba8c6520e926f361fe3aacc780413599f3a07404 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Tue, 19 Mar 2019 17:33:37 -0400 Subject: [PATCH 01/20] Progress --- .../tools/jib/api/JavaContainerBuilder.java | 36 +++- .../jib/gradle/GradleLayerConfigurations.java | 201 ------------------ .../jib/gradle/GradleProjectProperties.java | 117 ++++++++-- .../jib/maven/MavenLayerConfigurations.java | 172 --------------- .../jib/maven/MavenProjectProperties.java | 95 ++++++--- .../common/JavaContainerBuilderHelper.java | 107 ++++++++++ .../common/JavaLayerConfigurationsHelper.java | 95 --------- .../jib/plugins/common/MainClassResolver.java | 13 +- .../common/PluginConfigurationProcessor.java | 5 +- .../jib/plugins/common/ProjectProperties.java | 9 +- ...va => JavaContainerBuilderHelperTest.java} | 6 +- 11 files changed, 318 insertions(+), 538 deletions(-) delete mode 100644 jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurations.java delete mode 100644 jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurations.java create mode 100644 jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java delete mode 100644 jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelper.java rename jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/{JavaLayerConfigurationsHelperTest.java => JavaContainerBuilderHelperTest.java} (97%) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index fc01bbb07f..61d9e01395 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -127,7 +127,7 @@ public static JavaContainerBuilder from(RegistryImage registryImage) { // Keeps track of files to add to the image, by system path private final List addedResources = new ArrayList<>(); private final List addedClasses = new ArrayList<>(); - private final List addedDependencies = new ArrayList<>(); + private final List addedDependencies = new ArrayList<>(); private final List addedOthers = new ArrayList<>(); private AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); @@ -227,8 +227,8 @@ public JavaContainerBuilder addDependencies(List dependencyFiles) throws I if (!Files.exists(file)) { throw new NoSuchFileException(file.toString()); } + addedDependencies.add(new PathPredicatePair(file, path -> true)); } - addedDependencies.addAll(dependencyFiles); classpathOrder.add(LayerType.DEPENDENCIES); return this; } @@ -245,6 +245,21 @@ public JavaContainerBuilder addDependencies(Path... dependencyFiles) throws IOEx return addDependencies(Arrays.asList(dependencyFiles)); } + /** + * Adds dependency JARs to the image. Duplicate JAR filenames are renamed with the filesize in + * order to avoid collisions. + * + * @param dependenciesDirectory the directory containing dependency JARs to add to the image + * @param pathFilter filter that determines which files (not directories) should be added + * @return this + * @throws IOException if adding the layer fails + */ + public JavaContainerBuilder addDependencies( + Path dependenciesDirectory, Predicate pathFilter) throws IOException { + classpathOrder.add(LayerType.DEPENDENCIES); + return addDirectory(addedDependencies, dependenciesDirectory, pathFilter); + } + /** * Adds the contents of a resources directory to the image. * @@ -425,6 +440,7 @@ public JibContainerBuilder toContainerBuilder() throws IOException { List duplicates = addedDependencies .stream() + .map(entry -> entry.path) .map(Path::getFileName) .map(Path::toString) .collect(Collectors.groupingBy(filename -> filename, Collectors.counting())) @@ -433,22 +449,24 @@ public JibContainerBuilder toContainerBuilder() throws IOException { .filter(entry -> entry.getValue() > 1) .map(Entry::getKey) .collect(Collectors.toList()); - for (Path file : addedDependencies) { + for (PathPredicatePair pathPredicatePair : addedDependencies) { // Add dependencies to layer configuration layerConfigurationsBuilder.addFile( - file.getFileName().toString().contains("SNAPSHOT") + pathPredicatePair.path.getFileName().toString().contains("SNAPSHOT") ? LayerType.SNAPSHOT_DEPENDENCIES : LayerType.DEPENDENCIES, - file, + pathPredicatePair.path, appRoot .resolve(dependenciesDestination) .resolve( - duplicates.contains(file.getFileName().toString()) - ? file.getFileName() + duplicates.contains(pathPredicatePair.path.getFileName().toString()) + ? pathPredicatePair + .path + .getFileName() .toString() - .replaceFirst("\\.jar$", "-" + Files.size(file)) + .replaceFirst("\\.jar$", "-" + Files.size(pathPredicatePair.path)) + ".jar" - : file.getFileName().toString())); + : pathPredicatePair.path.getFileName().toString())); } // Add others to layer configuration diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurations.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurations.java deleted file mode 100644 index fb6d1392c2..0000000000 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurations.java +++ /dev/null @@ -1,201 +0,0 @@ -/* - * Copyright 2018 Google LLC. - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations under - * the License. - */ - -package com.google.cloud.tools.jib.gradle; - -import com.google.cloud.tools.jib.configuration.FilePermissions; -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaEntrypointConstructor; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; -import com.google.cloud.tools.jib.plugins.common.JavaLayerConfigurationsHelper; -import java.io.File; -import java.io.IOException; -import java.nio.file.Files; -import java.nio.file.Path; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.stream.Collectors; -import org.gradle.api.Project; -import org.gradle.api.file.FileCollection; -import org.gradle.api.logging.Logger; -import org.gradle.api.plugins.JavaPluginConvention; -import org.gradle.api.tasks.SourceSet; - -/** Builds {@link JavaLayerConfigurations} based on inputs from a {@link Project}. */ -class GradleLayerConfigurations { - - /** Name of the `main` {@link SourceSet} to use as source files. */ - private static final String MAIN_SOURCE_SET_NAME = "main"; - - /** - * Resolves the {@link JavaLayerConfigurations} for a Gradle {@link Project}. - * - * @param project the Gradle {@link Project} - * @param logger the logger for providing feedback about the resolution - * @param extraDirectory path to the source directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return {@link JavaLayerConfigurations} for the layers for the Gradle {@link Project} - * @throws IOException if an I/O exception occurred during resolution - */ - static JavaLayerConfigurations getForProject( - Project project, - Logger logger, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - if (TaskCommon.getWarTask(project) != null) { - logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); - return getForWarProject(project, extraDirectory, extraDirectoryPermissions, appRoot); - } else { - return getForNonWarProject( - project, logger, extraDirectory, extraDirectoryPermissions, appRoot); - } - } - - /** - * Resolves the {@link JavaLayerConfigurations} for a non-WAR Gradle {@link Project}. - * - * @param project the Gradle {@link Project} - * @param logger the logger for providing feedback about the resolution - * @param extraDirectory path to the source directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return {@link JavaLayerConfigurations} for the layers for the Gradle {@link Project} - * @throws IOException if an I/O exception occurred during resolution - */ - private static JavaLayerConfigurations getForNonWarProject( - Project project, - Logger logger, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - AbsoluteUnixPath dependenciesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_DEPENDENCIES_PATH_ON_IMAGE); - AbsoluteUnixPath resourcesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_RESOURCES_PATH_ON_IMAGE); - AbsoluteUnixPath classesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_CLASSES_PATH_ON_IMAGE); - - JavaLayerConfigurations.Builder layerBuilder = JavaLayerConfigurations.builder(); - - JavaPluginConvention javaPluginConvention = - project.getConvention().getPlugin(JavaPluginConvention.class); - SourceSet mainSourceSet = javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); - - FileCollection classesOutputDirectories = mainSourceSet.getOutput().getClassesDirs(); - Path resourcesOutputDirectory = mainSourceSet.getOutput().getResourcesDir().toPath(); - FileCollection allFiles = mainSourceSet.getRuntimeClasspath(); - FileCollection dependencyFiles = - allFiles - .minus(classesOutputDirectories) - .filter(file -> !file.toPath().equals(resourcesOutputDirectory)); - - // Adds class files. - logger.info("Adding corresponding output directories of source sets to image"); - for (File classesOutputDirectory : classesOutputDirectories) { - if (Files.notExists(classesOutputDirectory.toPath())) { - logger.info("\t'" + classesOutputDirectory + "' (not found, skipped)"); - continue; - } - logger.info("\t'" + classesOutputDirectory + "'"); - layerBuilder.addDirectoryContents( - LayerType.CLASSES, classesOutputDirectory.toPath(), path -> true, classesExtractionPath); - } - if (classesOutputDirectories.filter(File::exists).isEmpty()) { - logger.warn("No classes files were found - did you compile your project?"); - } - - // Adds resource files. - if (Files.exists(resourcesOutputDirectory)) { - layerBuilder.addDirectoryContents( - LayerType.RESOURCES, resourcesOutputDirectory, path -> true, resourcesExtractionPath); - } - - // Adds dependency files. - List duplicates = - dependencyFiles - .getFiles() - .stream() - .map(File::getName) - .collect(Collectors.groupingBy(filename -> filename, Collectors.counting())) - .entrySet() - .stream() - .filter(entry -> entry.getValue() > 1) - .map(Entry::getKey) - .collect(Collectors.toList()); - for (File dependencyFile : dependencyFiles) { - if (dependencyFile.exists()) { - boolean isSnapshot = dependencyFile.getName().contains("SNAPSHOT"); - LayerType layerType = isSnapshot ? LayerType.SNAPSHOT_DEPENDENCIES : LayerType.DEPENDENCIES; - layerBuilder.addFile( - layerType, - dependencyFile.toPath(), - dependenciesExtractionPath.resolve( - duplicates.contains(dependencyFile.getName()) - ? dependencyFile - .getName() - .replaceFirst("\\.jar$", "-" + Files.size(dependencyFile.toPath())) - + ".jar" - : dependencyFile.getName())); - } else { - logger.info("\t'" + dependencyFile + "' (not found, skipped)"); - } - } - - // Adds all the extra files. - if (Files.exists(extraDirectory)) { - layerBuilder.addDirectoryContents( - LayerType.EXTRA_FILES, - extraDirectory, - path -> true, - AbsoluteUnixPath.get("/"), - extraDirectoryPermissions); - } - - return layerBuilder.build(); - } - - /** - * Resolves the {@link JavaLayerConfigurations} for a WAR Gradle {@link Project}. - * - * @param project the Gradle {@link Project} - * @param extraDirectory path to the source directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return {@link JavaLayerConfigurations} for the layers for the Gradle {@link Project} - * @throws IOException if an I/O exception occurred during resolution - */ - private static JavaLayerConfigurations getForWarProject( - Project project, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - Path explodedWarPath = GradleProjectProperties.getExplodedWarDirectory(project); - return JavaLayerConfigurationsHelper.fromExplodedWar( - explodedWarPath, appRoot, extraDirectory, extraDirectoryPermissions); - } - - private GradleLayerConfigurations() {} -} diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index 156110cc5a..e79b849c04 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -16,13 +16,17 @@ package com.google.cloud.tools.jib.gradle; +import com.google.cloud.tools.jib.api.JavaContainerBuilder; +import com.google.cloud.tools.jib.api.JibContainerBuilder; +import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEventType; import com.google.cloud.tools.jib.event.events.LogEvent; import com.google.cloud.tools.jib.event.progress.ProgressEventHandler; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.filesystem.DirectoryWalker; +import com.google.cloud.tools.jib.plugins.common.JavaLayerConfigurationsHelper; import com.google.cloud.tools.jib.plugins.common.ProjectProperties; import com.google.cloud.tools.jib.plugins.common.PropertyNames; import com.google.cloud.tools.jib.plugins.common.TimerEventHandler; @@ -31,6 +35,7 @@ import com.google.cloud.tools.jib.plugins.common.logging.ProgressDisplayGenerator; import com.google.cloud.tools.jib.plugins.common.logging.SingleThreadedExecutor; import com.google.common.annotations.VisibleForTesting; +import com.google.common.collect.ImmutableList; import java.io.File; import java.io.IOException; import java.nio.file.Files; @@ -41,6 +46,7 @@ import java.util.Map; import java.util.Map.Entry; import java.util.Set; +import java.util.stream.Collectors; import javax.annotation.Nullable; import org.apache.tools.ant.taskdefs.condition.Os; import org.gradle.api.GradleException; @@ -50,6 +56,7 @@ import org.gradle.api.file.FileCollection; import org.gradle.api.logging.Logger; import org.gradle.api.plugins.JavaPluginConvention; +import org.gradle.api.tasks.SourceSet; import org.gradle.jvm.tasks.Jar; /** Obtains information about a Gradle {@link Project} that uses Jib. */ @@ -64,6 +71,9 @@ class GradleProjectProperties implements ProjectProperties { /** Used for logging during main class inference. */ private static final String JAR_PLUGIN_NAME = "'jar' task"; + /** Name of the `main` {@link SourceSet} to use as source files. */ + private static final String MAIN_SOURCE_SET_NAME = "main"; + /** @return a GradleProjectProperties from the given project and logger. */ static GradleProjectProperties getForProject( Project project, @@ -71,16 +81,8 @@ static GradleProjectProperties getForProject( Path extraDirectory, Map permissions, AbsoluteUnixPath appRoot) { - try { - return new GradleProjectProperties( - project, - logger, - GradleLayerConfigurations.getForProject( - project, logger, extraDirectory, convertPermissionsMap(permissions), appRoot)); - - } catch (IOException ex) { - throw new GradleException("Obtaining project build output files failed", ex); - } + return new GradleProjectProperties( + project, logger, extraDirectory, convertPermissionsMap(permissions), appRoot); } static Path getExplodedWarDirectory(Project project) { @@ -148,20 +150,103 @@ private static boolean isProgressFooterEnabled(Project project) { private final Project project; private final SingleThreadedExecutor singleThreadedExecutor = new SingleThreadedExecutor(); private final EventHandlers eventHandlers; - private final JavaLayerConfigurations javaLayerConfigurations; + private final Logger logger; + private final Path extraDirectory; + private final Map permissions; + private final AbsoluteUnixPath appRoot; @VisibleForTesting GradleProjectProperties( - Project project, Logger logger, JavaLayerConfigurations javaLayerConfigurations) { + Project project, + Logger logger, + Path extraDirectory, + Map permissions, + AbsoluteUnixPath appRoot) { this.project = project; - this.javaLayerConfigurations = javaLayerConfigurations; + this.logger = logger; + this.extraDirectory = extraDirectory; + this.permissions = permissions; + this.appRoot = appRoot; eventHandlers = makeEventHandlers(project, logger, singleThreadedExecutor); } @Override - public JavaLayerConfigurations getJavaLayerConfigurations() { - return javaLayerConfigurations; + public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) { + try { + if (TaskCommon.getWarTask(project) != null) { + logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); + Path explodedWarPath = GradleProjectProperties.getExplodedWarDirectory(project); + return JavaLayerConfigurationsHelper.fromExplodedWar( + baseImage, explodedWarPath, appRoot, extraDirectory, permissions); + } + + JavaPluginConvention javaPluginConvention = + project.getConvention().getPlugin(JavaPluginConvention.class); + SourceSet mainSourceSet = + javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); + + FileCollection classesOutputDirectories = + mainSourceSet.getOutput().getClassesDirs().filter(File::exists); + Path resourcesOutputDirectory = mainSourceSet.getOutput().getResourcesDir().toPath(); + FileCollection allFiles = mainSourceSet.getRuntimeClasspath(); + FileCollection dependencyFiles = + allFiles + .minus(classesOutputDirectories) + .filter(file -> !file.toPath().equals(resourcesOutputDirectory)); + + JavaContainerBuilder javaContainerBuilder = + JavaContainerBuilder.from(baseImage).setAppRoot(appRoot); + + // Adds resource files + if (Files.exists(resourcesOutputDirectory)) { + javaContainerBuilder.addResources(resourcesOutputDirectory); + } + + // Adds class files + for (File classesOutputDirectory : classesOutputDirectories) { + javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); + } + if (classesOutputDirectories.filter(File::exists).isEmpty()) { + logger.warn("No classes files were found - did you compile your project?"); + } + + // Adds dependency files + javaContainerBuilder.addDependencies( + dependencyFiles + .getFiles() + .stream() + .filter(File::exists) + .map(File::toPath) + .collect(Collectors.toList())); + + JibContainerBuilder jibContainerBuilder = javaContainerBuilder.toContainerBuilder(); + + // Adds all the extra files. + if (Files.exists(extraDirectory)) { + jibContainerBuilder.addLayer( + JavaLayerConfigurationsHelper.extraDirectoryLayerConfiguration( + extraDirectory, permissions)); + } + return jibContainerBuilder; + + } catch (IOException ex) { + throw new GradleException("Obtaining project build output files failed", ex); + } + } + + @Override + public ImmutableList getClassFiles() throws IOException { + // TODO: Consolidate with getContainerBuilderWithLayers + JavaPluginConvention javaPluginConvention = + project.getConvention().getPlugin(JavaPluginConvention.class); + SourceSet mainSourceSet = javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); + FileCollection classesOutputDirectories = mainSourceSet.getOutput().getClassesDirs(); + ImmutableList.Builder classFiles = ImmutableList.builder(); + for (File classesOutputDirectory : classesOutputDirectories) { + classFiles.addAll(new DirectoryWalker(classesOutputDirectory.toPath()).walk().asList()); + } + return classFiles.build(); } @Override diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurations.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurations.java deleted file mode 100644 index 07f0911be7..0000000000 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurations.java +++ /dev/null @@ -1,172 +0,0 @@ -/* - * Copyright 2018 Google LLC. - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations under - * the License. - */ - -package com.google.cloud.tools.jib.maven; - -import com.google.cloud.tools.jib.configuration.FilePermissions; -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaEntrypointConstructor; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; -import com.google.cloud.tools.jib.plugins.common.JavaLayerConfigurationsHelper; -import java.io.File; -import java.io.IOException; -import java.nio.file.Files; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.function.Predicate; -import java.util.stream.Collectors; -import org.apache.maven.artifact.Artifact; -import org.apache.maven.project.MavenProject; - -/** Builds {@link JavaLayerConfigurations} based on inputs from a {@link MavenProject}. */ -class MavenLayerConfigurations { - - /** - * Resolves the {@link JavaLayerConfigurations} for a {@link MavenProject}. - * - * @param project the {@link MavenProject} - * @param extraDirectory path to the directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return a {@link JavaLayerConfigurations} for the project - * @throws IOException if collecting the project files fails - */ - static JavaLayerConfigurations getForProject( - MavenProject project, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - if (MojoCommon.isWarProject(project)) { - return getForWarProject(project, extraDirectory, extraDirectoryPermissions, appRoot); - } else { - return getForNonWarProject(project, extraDirectory, extraDirectoryPermissions, appRoot); - } - } - - /** - * Resolves the {@link JavaLayerConfigurations} for a non-WAR {@link MavenProject}. - * - * @param project the {@link MavenProject} - * @param extraDirectory path to the directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return a {@link JavaLayerConfigurations} for the project - * @throws IOException if collecting the project files fails - */ - private static JavaLayerConfigurations getForNonWarProject( - MavenProject project, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - - AbsoluteUnixPath dependenciesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_DEPENDENCIES_PATH_ON_IMAGE); - AbsoluteUnixPath resourcesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_RESOURCES_PATH_ON_IMAGE); - AbsoluteUnixPath classesExtractionPath = - appRoot.resolve(JavaEntrypointConstructor.DEFAULT_RELATIVE_CLASSES_PATH_ON_IMAGE); - - JavaLayerConfigurations.Builder layerBuilder = JavaLayerConfigurations.builder(); - - // Gets all the dependencies. - List duplicates = - project - .getArtifacts() - .stream() - .map(Artifact::getFile) - .map(File::getName) - .collect(Collectors.groupingBy(filename -> filename, Collectors.counting())) - .entrySet() - .stream() - .filter(entry -> entry.getValue() > 1) - .map(Entry::getKey) - .collect(Collectors.toList()); - for (Artifact artifact : project.getArtifacts()) { - Path artifactPath = artifact.getFile().toPath(); - LayerType layerType = - artifact.isSnapshot() ? LayerType.SNAPSHOT_DEPENDENCIES : LayerType.DEPENDENCIES; - String filename = artifactPath.getFileName().toString(); - layerBuilder.addFile( - layerType, - artifactPath, - dependenciesExtractionPath.resolve( - duplicates.contains(filename) - ? filename.replaceFirst("\\.jar$", "-" + Files.size(artifactPath)) + ".jar" - : filename)); - } - - Path classesOutputDirectory = Paths.get(project.getBuild().getOutputDirectory()); - - // Gets the classes files in the 'classes' output directory. - Predicate isClassFile = path -> path.getFileName().toString().endsWith(".class"); - layerBuilder.addDirectoryContents( - LayerType.CLASSES, classesOutputDirectory, isClassFile, classesExtractionPath); - - // Gets the resources files in the 'classes' output directory. - layerBuilder.addDirectoryContents( - LayerType.RESOURCES, classesOutputDirectory, isClassFile.negate(), resourcesExtractionPath); - - // Adds all the extra files. - if (Files.exists(extraDirectory)) { - layerBuilder.addDirectoryContents( - LayerType.EXTRA_FILES, - extraDirectory, - path -> true, - AbsoluteUnixPath.get("/"), - extraDirectoryPermissions); - } - - return layerBuilder.build(); - } - - /** - * Resolves the {@link JavaLayerConfigurations} for a WAR {@link MavenProject}. - * - * @param project the {@link MavenProject} - * @param extraDirectory path to the directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions for extra-layer - * files - * @param appRoot root directory in the image where the app will be placed - * @return a {@link JavaLayerConfigurations} for the project - * @throws IOException if collecting the project files fails - */ - private static JavaLayerConfigurations getForWarProject( - MavenProject project, - Path extraDirectory, - Map extraDirectoryPermissions, - AbsoluteUnixPath appRoot) - throws IOException { - - // TODO explode the WAR file rather than using this directory. The contents of the final WAR may - // be different from this directory (it's possible to include or exclude files when packaging a - // WAR). Also the exploded WAR directory is configurable with and may not be - // at build.getFinalName(). - Path explodedWarPath = - Paths.get(project.getBuild().getDirectory()).resolve(project.getBuild().getFinalName()); - return JavaLayerConfigurationsHelper.fromExplodedWar( - explodedWarPath, appRoot, extraDirectory, extraDirectoryPermissions); - } - - private MavenLayerConfigurations() {} -} diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index d975f4c0b5..661674042e 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -16,13 +16,17 @@ package com.google.cloud.tools.jib.maven; +import com.google.cloud.tools.jib.api.JavaContainerBuilder; +import com.google.cloud.tools.jib.api.JibContainerBuilder; +import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEventType; import com.google.cloud.tools.jib.event.events.LogEvent; import com.google.cloud.tools.jib.event.progress.ProgressEventHandler; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.filesystem.DirectoryWalker; +import com.google.cloud.tools.jib.plugins.common.JavaContainerBuilderHelper; import com.google.cloud.tools.jib.plugins.common.ProjectProperties; import com.google.cloud.tools.jib.plugins.common.PropertyNames; import com.google.cloud.tools.jib.plugins.common.TimerEventHandler; @@ -31,14 +35,19 @@ import com.google.cloud.tools.jib.plugins.common.logging.ProgressDisplayGenerator; import com.google.cloud.tools.jib.plugins.common.logging.SingleThreadedExecutor; import com.google.common.annotations.VisibleForTesting; +import com.google.common.collect.ImmutableList; +import java.io.File; import java.io.IOException; +import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; import java.util.Map; +import java.util.function.Predicate; +import java.util.stream.Collectors; import javax.annotation.Nullable; +import org.apache.maven.artifact.Artifact; import org.apache.maven.execution.MavenSession; import org.apache.maven.model.Plugin; -import org.apache.maven.plugin.MojoExecutionException; import org.apache.maven.plugin.logging.Log; import org.apache.maven.project.MavenProject; import org.apache.maven.shared.utils.Os; @@ -67,7 +76,6 @@ public class MavenProjectProperties implements ProjectProperties { * @param permissions map from path on container to file permissions for extra-layer files * @param appRoot root directory in the image where the app will be placed * @return a MavenProjectProperties from the given project and logger. - * @throws MojoExecutionException if no class files are found in the output directory. */ static MavenProjectProperties getForProject( MavenProject project, @@ -75,22 +83,8 @@ static MavenProjectProperties getForProject( Log log, Path extraDirectory, Map permissions, - AbsoluteUnixPath appRoot) - throws MojoExecutionException { - try { - return new MavenProjectProperties( - project, - session, - log, - MavenLayerConfigurations.getForProject(project, extraDirectory, permissions, appRoot)); - - } catch (IOException ex) { - throw new MojoExecutionException( - "Obtaining project build output files failed; make sure you have compiled your project " - + "before trying to build the image. (Did you accidentally run \"mvn clean " - + "jib:build\" instead of \"mvn clean compile jib:build\"?)", - ex); - } + AbsoluteUnixPath appRoot) { + return new MavenProjectProperties(project, session, log, extraDirectory, permissions, appRoot); } /** @@ -200,23 +194,74 @@ static int getVersionFromString(String versionString) { private final MavenProject project; private final SingleThreadedExecutor singleThreadedExecutor = new SingleThreadedExecutor(); private final EventHandlers eventHandlers; - private final JavaLayerConfigurations javaLayerConfigurations; + private final Path extraDirectory; + private final Map permissions; + private final AbsoluteUnixPath appRoot; @VisibleForTesting MavenProjectProperties( MavenProject project, MavenSession session, Log log, - JavaLayerConfigurations javaLayerConfigurations) { + Path extraDirectory, + Map permissions, + AbsoluteUnixPath appRoot) { this.project = project; - this.javaLayerConfigurations = javaLayerConfigurations; - + this.extraDirectory = extraDirectory; + this.permissions = permissions; + this.appRoot = appRoot; eventHandlers = makeEventHandlers(session, log, singleThreadedExecutor); } @Override - public JavaLayerConfigurations getJavaLayerConfigurations() { - return javaLayerConfigurations; + public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) + throws IOException { + try { + if (MojoCommon.isWarProject(project)) { + Path explodedWarPath = + Paths.get(project.getBuild().getDirectory()).resolve(project.getBuild().getFinalName()); + return JavaContainerBuilderHelper.fromExplodedWar( + baseImage, explodedWarPath, appRoot, extraDirectory, permissions); + } + + Path classesOutputDirectory = Paths.get(project.getBuild().getOutputDirectory()); + Predicate isClassFile = path -> path.getFileName().toString().endsWith(".class"); + + // Add dependencies, resources, and classes + JibContainerBuilder jibContainerBuilder = + JavaContainerBuilder.from(baseImage) + .setAppRoot(appRoot) + .addResources(classesOutputDirectory, isClassFile.negate()) + .addClasses(classesOutputDirectory, isClassFile) + .addDependencies( + project + .getArtifacts() + .stream() + .map(Artifact::getFile) + .map(File::toPath) + .collect(Collectors.toList())) + .toContainerBuilder(); + + // Adds all the extra files. + if (Files.exists(extraDirectory)) { + jibContainerBuilder.addLayer( + JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( + extraDirectory, permissions)); + } + return jibContainerBuilder; + + } catch (IOException ex) { + throw new IOException( + "Obtaining project build output files failed; make sure you have compiled your project " + + "before trying to build the image. (Did you accidentally run \"mvn clean " + + "jib:build\" instead of \"mvn clean compile jib:build\"?)", + ex); + } + } + + @Override + public ImmutableList getClassFiles() throws IOException { + return new DirectoryWalker(Paths.get(project.getBuild().getOutputDirectory())).walk().asList(); } @Override diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java new file mode 100644 index 0000000000..01eb1d44ed --- /dev/null +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -0,0 +1,107 @@ +/* + * Copyright 2018 Google LLC. + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not + * use this file except in compliance with the License. You may obtain a copy of + * the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations under + * the License. + */ + +package com.google.cloud.tools.jib.plugins.common; + +import com.google.cloud.tools.jib.api.JavaContainerBuilder; +import com.google.cloud.tools.jib.api.JibContainerBuilder; +import com.google.cloud.tools.jib.api.RegistryImage; +import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.configuration.LayerConfiguration; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; +import com.google.cloud.tools.jib.filesystem.DirectoryWalker; +import com.google.cloud.tools.jib.filesystem.RelativeUnixPath; +import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.Map; +import java.util.function.Predicate; + +/** Helper for constructing {@link JavaLayerConfigurations}. */ +public class JavaContainerBuilderHelper { + + /** + * Returns a {@link LayerConfiguration} for adding the extra directory to the container. + * + * @param extraDirectory the source extra directory path + * @param extraDirectoryPermissions map from path on container to file permissions + * @return a {@link LayerConfiguration} for adding the extra directory to the container + * @throws IOException if walking the extra directory fails + */ + public static LayerConfiguration extraDirectoryLayerConfiguration( + Path extraDirectory, Map extraDirectoryPermissions) + throws IOException { + LayerConfiguration.Builder builder = LayerConfiguration.builder().setName("extra files"); + new DirectoryWalker(extraDirectory) + .filterRoot() + .walk( + path -> { + AbsoluteUnixPath pathOnContainer = + AbsoluteUnixPath.get("/").resolve(extraDirectory.relativize(path)); + builder.addEntry( + path, pathOnContainer, extraDirectoryPermissions.get(pathOnContainer)); + }); + return builder.build(); + } + + /** + * Constructs a new {@link JavaLayerConfigurations} for a WAR project. + * + * @param explodedWar the exploded WAR directory + * @param appRoot root directory in the image where the app will be placed + * @param extraFilesDirectory path to the source directory for the extra files layer + * @param extraDirectoryPermissions map from path on container to file permissions + * @return {@link JavaLayerConfigurations} for the layers for the exploded WAR + * @throws IOException if adding layer contents fails + */ + public static JibContainerBuilder fromExplodedWar( + RegistryImage baseImage, + Path explodedWar, + AbsoluteUnixPath appRoot, + Path extraFilesDirectory, + Map extraDirectoryPermissions) + throws IOException { + Path webInfLib = explodedWar.resolve("WEB-INF/lib"); + Path webInfClasses = explodedWar.resolve("WEB-INF/classes"); + Predicate isDependency = path -> path.startsWith(webInfLib); + Predicate isClassFile = + path -> path.startsWith(webInfClasses) && path.getFileName().toString().endsWith(".class"); + Predicate isResource = isDependency.or(isClassFile).negate(); + + JibContainerBuilder jibContainerBuilder = + JavaContainerBuilder.from(baseImage) + .setAppRoot(appRoot) + .setResourcesDestination(RelativeUnixPath.get("")) + .setClassesDestination(RelativeUnixPath.get("WEB-INF/classes")) + .setDependenciesDestination(RelativeUnixPath.get("WEB-INF/lib")) + .addResources(explodedWar, isResource) + .addClasses(webInfClasses, isClassFile) + .addDependencies(webInfLib, isDependency) + .toContainerBuilder(); + + // Adds all the extra files. + if (Files.exists(extraFilesDirectory)) { + jibContainerBuilder.addLayer( + JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( + extraFilesDirectory, extraDirectoryPermissions)); + } + + return jibContainerBuilder; + } + + private JavaContainerBuilderHelper() {} +} diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelper.java deleted file mode 100644 index aec8abeef6..0000000000 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelper.java +++ /dev/null @@ -1,95 +0,0 @@ -/* - * Copyright 2018 Google LLC. - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations under - * the License. - */ - -package com.google.cloud.tools.jib.plugins.common; - -import com.google.cloud.tools.jib.configuration.FilePermissions; -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; -import java.io.IOException; -import java.nio.file.Files; -import java.nio.file.Path; -import java.util.Map; -import java.util.function.Predicate; - -/** Helper for constructing {@link JavaLayerConfigurations}. */ -public class JavaLayerConfigurationsHelper { - - /** - * Constructs a new {@link JavaLayerConfigurations} for a WAR project. - * - * @param explodedWar the exploded WAR directory - * @param appRoot root directory in the image where the app will be placed - * @param extraFilesDirectory path to the source directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions - * @return {@link JavaLayerConfigurations} for the layers for the exploded WAR - * @throws IOException if adding layer contents fails - */ - public static JavaLayerConfigurations fromExplodedWar( - Path explodedWar, - AbsoluteUnixPath appRoot, - Path extraFilesDirectory, - Map extraDirectoryPermissions) - throws IOException { - Path webInfLib = explodedWar.resolve("WEB-INF/lib"); - Path webInfClasses = explodedWar.resolve("WEB-INF/classes"); - - Predicate nameHasSnapshot = path -> path.getFileName().toString().contains("SNAPSHOT"); - Predicate isSnapshotDependency = - path -> path.startsWith(webInfLib) && nameHasSnapshot.test(path); - Predicate isNonSnapshotDependency = - path -> path.startsWith(webInfLib) && !nameHasSnapshot.test(path); - Predicate isClassFile = - path -> path.startsWith(webInfClasses) && path.getFileName().toString().endsWith(".class"); - Predicate isResource = - isSnapshotDependency.or(isNonSnapshotDependency).or(isClassFile).negate(); - - JavaLayerConfigurations.Builder layerBuilder = JavaLayerConfigurations.builder(); - - // Gets all the dependencies. - if (Files.exists(webInfLib)) { - AbsoluteUnixPath basePathInContainer = appRoot.resolve("WEB-INF/lib"); - layerBuilder.addDirectoryContents( - LayerType.DEPENDENCIES, webInfLib, isNonSnapshotDependency, basePathInContainer); - layerBuilder.addDirectoryContents( - LayerType.SNAPSHOT_DEPENDENCIES, webInfLib, isSnapshotDependency, basePathInContainer); - } - - // Gets the classes files in the 'WEB-INF/classes' output directory. - if (Files.exists(webInfClasses)) { - layerBuilder.addDirectoryContents( - LayerType.CLASSES, webInfClasses, isClassFile, appRoot.resolve("WEB-INF/classes")); - } - - // Gets the resources. - layerBuilder.addDirectoryContents(LayerType.RESOURCES, explodedWar, isResource, appRoot); - - // Adds all the extra files. - if (Files.exists(extraFilesDirectory)) { - layerBuilder.addDirectoryContents( - LayerType.EXTRA_FILES, - extraFilesDirectory, - path -> true, - AbsoluteUnixPath.get("/"), - extraDirectoryPermissions); - } - - return layerBuilder.build(); - } - - private JavaLayerConfigurationsHelper() {} -} diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java index 1f9d7a9b88..ab4c892604 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java @@ -19,12 +19,9 @@ import com.google.cloud.tools.jib.event.DefaultEventDispatcher; import com.google.cloud.tools.jib.event.events.LogEvent; import com.google.cloud.tools.jib.frontend.MainClassFinder; -import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.annotations.VisibleForTesting; import com.google.common.base.Preconditions; import com.google.common.base.Splitter; -import com.google.common.collect.ImmutableList; -import java.nio.file.Path; import javax.annotation.Nullable; import javax.lang.model.SourceVersion; @@ -114,17 +111,9 @@ private static String findMainClassInClassFiles(ProjectProperties projectPropert + projectProperties.getJarPluginName() + "; attempting to infer main class.")); - ImmutableList classesSourceFiles = - projectProperties - .getJavaLayerConfigurations() - .getClassLayerEntries() - .stream() - .map(LayerEntry::getSourceFile) - .collect(ImmutableList.toImmutableList()); - MainClassFinder.Result mainClassFinderResult = new MainClassFinder( - classesSourceFiles, + projectProperties.getClassFiles(), new DefaultEventDispatcher(projectProperties.getEventHandlers())) .find(); diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java index 853334756b..014fc27003 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java @@ -18,7 +18,6 @@ import com.google.cloud.tools.jib.api.Containerizer; import com.google.cloud.tools.jib.api.DockerDaemonImage; -import com.google.cloud.tools.jib.api.Jib; import com.google.cloud.tools.jib.api.JibContainerBuilder; import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.api.TarImage; @@ -187,8 +186,8 @@ static PluginConfigurationProcessor processCommonConfiguration( rawConfiguration.getFromCredHelper().orElse(null)); JibContainerBuilder jibContainerBuilder = - Jib.from(baseImage) - .setLayers(projectProperties.getJavaLayerConfigurations().getLayerConfigurations()) + projectProperties + .getContainerBuilderWithLayers(baseImage) .setEntrypoint(computeEntrypoint(rawConfiguration, projectProperties)) .setProgramArguments(rawConfiguration.getProgramArguments().orElse(null)) .setEnvironment(rawConfiguration.getEnvironment()) diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java index aaaefb6d9b..52f9cb25d3 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java @@ -16,8 +16,11 @@ package com.google.cloud.tools.jib.plugins.common; +import com.google.cloud.tools.jib.api.JibContainerBuilder; +import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.event.EventHandlers; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.common.collect.ImmutableList; +import java.io.IOException; import java.nio.file.Path; import javax.annotation.Nullable; @@ -43,7 +46,9 @@ public interface ProjectProperties { String getPluginName(); - JavaLayerConfigurations getJavaLayerConfigurations(); + JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) throws IOException; + + ImmutableList getClassFiles() throws IOException; Path getDefaultCacheDirectory(); diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelperTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java similarity index 97% rename from jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelperTest.java rename to jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java index 02197686b9..9002c8a55b 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaLayerConfigurationsHelperTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java @@ -37,8 +37,8 @@ import org.junit.Test; import org.junit.rules.TemporaryFolder; -/** Tests for {@link JavaLayerConfigurationsHelper}. */ -public class JavaLayerConfigurationsHelperTest { +/** Tests for {@link JavaContainerBuilderHelper}. */ +public class JavaContainerBuilderHelperTest { private static void assertLayerEntriesUnordered( List expectedPaths, List entries, Function fieldSelector) { @@ -72,7 +72,7 @@ public void testFromExplodedWar() throws URISyntaxException, IOException { Path extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); JavaLayerConfigurations configuration = - JavaLayerConfigurationsHelper.fromExplodedWar( + JavaContainerBuilderHelper.fromExplodedWar( temporaryExplodedWar, AbsoluteUnixPath.get("/my/app"), extraFilesDirectory, From 54aee3db061133c5ea33e92ca6384e5a5a2ee174 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 12:40:20 -0400 Subject: [PATCH 02/20] Progress --- .../tools/jib/api/JavaContainerBuilder.java | 10 ++- .../tools/jib/api/JibContainerBuilder.java | 2 +- .../jib/frontend/JavaLayerConfigurations.java | 2 +- .../common/JavaContainerBuilderHelper.java | 5 +- .../jib/plugins/common/MainClassResolver.java | 6 +- .../common/PluginConfigurationProcessor.java | 2 +- .../JavaContainerBuilderHelperTest.java | 84 +++++++++++++++---- .../plugins/common/MainClassResolverTest.java | 45 ++++------ .../PluginConfigurationProcessorTest.java | 13 +-- 9 files changed, 109 insertions(+), 60 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index 61d9e01395..bb5df8a753 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -18,6 +18,7 @@ import com.google.cloud.tools.jib.ProjectInfo; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; +import com.google.cloud.tools.jib.filesystem.DirectoryWalker; import com.google.cloud.tools.jib.filesystem.RelativeUnixPath; import com.google.cloud.tools.jib.frontend.JavaEntrypointConstructor; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; @@ -256,8 +257,13 @@ public JavaContainerBuilder addDependencies(Path... dependencyFiles) throws IOEx */ public JavaContainerBuilder addDependencies( Path dependenciesDirectory, Predicate pathFilter) throws IOException { - classpathOrder.add(LayerType.DEPENDENCIES); - return addDirectory(addedDependencies, dependenciesDirectory, pathFilter); + return addDependencies( + new DirectoryWalker(dependenciesDirectory) + .filterRoot() + .filter(pathFilter) + .filter(path -> !Files.isDirectory(path)) + .walk() + .asList()); } /** diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JibContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JibContainerBuilder.java index 6f72a43475..a678b093d0 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JibContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JibContainerBuilder.java @@ -525,7 +525,7 @@ JibContainer containerize( * @throws IOException if an I/O exception occurs */ @VisibleForTesting - BuildConfiguration toBuildConfiguration( + public BuildConfiguration toBuildConfiguration( Containerizer containerizer, ExecutorService executorService) throws CacheDirectoryCreationException, IOException { buildConfigurationBuilder diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java index 8a9dd1f593..bbe780c00f 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java @@ -57,7 +57,7 @@ public enum LayerType { } @VisibleForTesting - String getName() { + public String getName() { return name; } } diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index 01eb1d44ed..dc6e186312 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -25,6 +25,7 @@ import com.google.cloud.tools.jib.filesystem.DirectoryWalker; import com.google.cloud.tools.jib.filesystem.RelativeUnixPath; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; import java.io.IOException; import java.nio.file.Files; import java.nio.file.Path; @@ -45,7 +46,8 @@ public class JavaContainerBuilderHelper { public static LayerConfiguration extraDirectoryLayerConfiguration( Path extraDirectory, Map extraDirectoryPermissions) throws IOException { - LayerConfiguration.Builder builder = LayerConfiguration.builder().setName("extra files"); + LayerConfiguration.Builder builder = + LayerConfiguration.builder().setName(LayerType.EXTRA_FILES.getName()); new DirectoryWalker(extraDirectory) .filterRoot() .walk( @@ -61,6 +63,7 @@ public static LayerConfiguration extraDirectoryLayerConfiguration( /** * Constructs a new {@link JavaLayerConfigurations} for a WAR project. * + * @param baseImage the base image of the container * @param explodedWar the exploded WAR directory * @param appRoot root directory in the image where the app will be placed * @param extraFilesDirectory path to the source directory for the extra files layer diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java index ab4c892604..990ea36c99 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/MainClassResolver.java @@ -22,6 +22,7 @@ import com.google.common.annotations.VisibleForTesting; import com.google.common.base.Preconditions; import com.google.common.base.Splitter; +import java.io.IOException; import javax.annotation.Nullable; import javax.lang.model.SourceVersion; @@ -44,10 +45,11 @@ public class MainClassResolver { * @param projectProperties properties containing plugin information and help messages * @return the name of the main class to be used for the container entrypoint * @throws MainClassInferenceException if no valid main class is configured or discovered + * @throws IOException if getting the class files from {@code projectProperties} fails */ public static String resolveMainClass( @Nullable String mainClass, ProjectProperties projectProperties) - throws MainClassInferenceException { + throws MainClassInferenceException, IOException { // If mainClass is null, try to find via projectProperties. if (mainClass == null) { mainClass = getMainClassFromJar(projectProperties); @@ -103,7 +105,7 @@ private static String getMainClassFromJar(ProjectProperties projectProperties) { } private static String findMainClassInClassFiles(ProjectProperties projectProperties) - throws MainClassInferenceException { + throws MainClassInferenceException, IOException { new DefaultEventDispatcher(projectProperties.getEventHandlers()) .dispatch( LogEvent.debug( diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java index 014fc27003..3606a2a9dc 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java @@ -236,7 +236,7 @@ static PluginConfigurationProcessor processCommonConfiguration( @VisibleForTesting static List computeEntrypoint( RawConfiguration rawConfiguration, ProjectProperties projectProperties) - throws MainClassInferenceException, InvalidAppRootException { + throws MainClassInferenceException, InvalidAppRootException, IOException { Optional> rawEntrypoint = rawConfiguration.getEntrypoint(); if (rawEntrypoint.isPresent() && !rawEntrypoint.get().isEmpty()) { if (rawConfiguration.getMainClass().isPresent() diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java index 9002c8a55b..c70bc850b8 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java @@ -16,12 +16,19 @@ package com.google.cloud.tools.jib.plugins.common; +import com.google.cloud.tools.jib.api.Containerizer; +import com.google.cloud.tools.jib.api.RegistryImage; +import com.google.cloud.tools.jib.configuration.BuildConfiguration; +import com.google.cloud.tools.jib.configuration.CacheDirectoryCreationException; +import com.google.cloud.tools.jib.configuration.LayerConfiguration; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.filesystem.FileOperations; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; +import com.google.cloud.tools.jib.image.InvalidImageReferenceException; import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.collect.ImmutableList; import com.google.common.io.Resources; +import com.google.common.util.concurrent.MoreExecutors; import java.io.IOException; import java.net.URISyntaxException; import java.nio.file.Files; @@ -58,10 +65,38 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } + private static List getLayerConfigurationByName( + BuildConfiguration buildConfiguration, String name) { + return buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals(name)) + .collect(Collectors.toList()); + } + @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @Test - public void testFromExplodedWar() throws URISyntaxException, IOException { + public void testExtraDirectoryLayerConfiguration() throws URISyntaxException, IOException { + Path extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + LayerConfiguration layerConfiguration = + JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( + extraFilesDirectory, Collections.emptyMap()); + assertSourcePathsUnordered( + Arrays.asList( + extraFilesDirectory.resolve("a"), + extraFilesDirectory.resolve("a/b"), + extraFilesDirectory.resolve("a/b/bar"), + extraFilesDirectory.resolve("c"), + extraFilesDirectory.resolve("c/cat"), + extraFilesDirectory.resolve("foo")), + layerConfiguration.getLayerEntries()); + } + + @Test + public void testFromExplodedWar() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { // Copy test files to a temporary directory that we can safely operate on Path resourceExplodedWar = Paths.get(Resources.getResource("plugins-common/exploded-war").toURI()); @@ -71,20 +106,35 @@ public void testFromExplodedWar() throws URISyntaxException, IOException { Files.createDirectories(temporaryExplodedWar.resolve("WEB-INF/classes/empty_dir")); Path extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); - JavaLayerConfigurations configuration = + BuildConfiguration configuration = JavaContainerBuilderHelper.fromExplodedWar( - temporaryExplodedWar, - AbsoluteUnixPath.get("/my/app"), - extraFilesDirectory, - Collections.emptyMap()); + RegistryImage.named("base"), + temporaryExplodedWar, + AbsoluteUnixPath.get("/my/app"), + extraFilesDirectory, + Collections.emptyMap()) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("target")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertSourcePathsUnordered( Collections.singletonList(temporaryExplodedWar.resolve("WEB-INF/lib/dependency-1.0.0.jar")), - configuration.getDependencyLayerEntries()); + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( Collections.singletonList( temporaryExplodedWar.resolve("WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")), - configuration.getSnapshotDependencyLayerEntries()); + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( Arrays.asList( temporaryExplodedWar.resolve("META-INF"), @@ -97,14 +147,14 @@ public void testFromExplodedWar() throws URISyntaxException, IOException { temporaryExplodedWar.resolve("WEB-INF/classes/package/test.properties"), temporaryExplodedWar.resolve("WEB-INF/lib"), temporaryExplodedWar.resolve("WEB-INF/web.xml")), - configuration.getResourceLayerEntries()); + resourcesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( Arrays.asList( temporaryExplodedWar.resolve("WEB-INF/classes/HelloWorld.class"), temporaryExplodedWar.resolve("WEB-INF/classes/empty_dir"), temporaryExplodedWar.resolve("WEB-INF/classes/package"), temporaryExplodedWar.resolve("WEB-INF/classes/package/Other.class")), - configuration.getClassLayerEntries()); + classesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( Arrays.asList( extraFilesDirectory.resolve("a"), @@ -113,14 +163,14 @@ public void testFromExplodedWar() throws URISyntaxException, IOException { extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), extraFilesDirectory.resolve("foo")), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/META-INF", @@ -133,16 +183,16 @@ public void testFromExplodedWar() throws URISyntaxException, IOException { "/my/app/WEB-INF/classes/package/test.properties", "/my/app/WEB-INF/lib", "/my/app/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); + resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/WEB-INF/classes/HelloWorld.class", "/my/app/WEB-INF/classes/empty_dir", "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); + classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); } } diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/MainClassResolverTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/MainClassResolverTest.java index 27d5452eca..95c5d44fcb 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/MainClassResolverTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/MainClassResolverTest.java @@ -19,10 +19,7 @@ import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEvent; import com.google.cloud.tools.jib.event.events.LogEvent; -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.filesystem.DirectoryWalker; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.collect.ImmutableList; import com.google.common.io.Resources; import java.io.IOException; @@ -47,7 +44,6 @@ public class MainClassResolverTest { @Mock private Consumer mockJibEventConsumer; @Mock private ProjectProperties mockProjectProperties; - @Mock private JavaLayerConfigurations mockJavaLayerConfigurations; @Before public void setup() { @@ -55,12 +51,10 @@ public void setup() { .thenReturn(new EventHandlers().add(mockJibEventConsumer)); Mockito.when(mockProjectProperties.getPluginName()).thenReturn("plugin"); Mockito.when(mockProjectProperties.getJarPluginName()).thenReturn("jar-plugin"); - Mockito.when(mockProjectProperties.getJavaLayerConfigurations()) - .thenReturn(mockJavaLayerConfigurations); } @Test - public void testResolveMainClass() throws MainClassInferenceException { + public void testResolveMainClass() throws MainClassInferenceException, IOException { Mockito.when(mockProjectProperties.getMainClassFromJar()).thenReturn("some.main.class"); Assert.assertEquals( "some.main.class", MainClassResolver.resolveMainClass(null, mockProjectProperties)); @@ -69,12 +63,10 @@ public void testResolveMainClass() throws MainClassInferenceException { } @Test - public void testResolveMainClass_notValid() throws MainClassInferenceException { + public void testResolveMainClass_notValid() throws MainClassInferenceException, IOException { Mockito.when(mockProjectProperties.getMainClassFromJar()).thenReturn("${start-class}"); - Mockito.when(mockProjectProperties.getJavaLayerConfigurations().getClassLayerEntries()) - .thenReturn( - ImmutableList.of( - new LayerEntry(FAKE_CLASSES_PATH, AbsoluteUnixPath.get("/ignored"), null))); + Mockito.when(mockProjectProperties.getClassFiles()) + .thenReturn(ImmutableList.of(FAKE_CLASSES_PATH)); Assert.assertEquals( "${start-class}", MainClassResolver.resolveMainClass(null, mockProjectProperties)); Mockito.verify(mockJibEventConsumer) @@ -85,14 +77,12 @@ public void testResolveMainClass_notValid() throws MainClassInferenceException { public void testResolveMainClass_multipleInferredWithBackup() throws MainClassInferenceException, URISyntaxException, IOException { Mockito.when(mockProjectProperties.getMainClassFromJar()).thenReturn("${start-class}"); - Mockito.when(mockProjectProperties.getJavaLayerConfigurations().getClassLayerEntries()) + Mockito.when(mockProjectProperties.getClassFiles()) .thenReturn( new DirectoryWalker( Paths.get(Resources.getResource("core/class-finder-tests/multiple").toURI())) .walk() - .stream() - .map(path -> new LayerEntry(path, AbsoluteUnixPath.get("/ignored"), null)) - .collect(ImmutableList.toImmutableList())); + .asList()); Assert.assertEquals( "${start-class}", MainClassResolver.resolveMainClass(null, mockProjectProperties)); Mockito.verify(mockJibEventConsumer) @@ -103,14 +93,12 @@ public void testResolveMainClass_multipleInferredWithBackup() public void testResolveMainClass_multipleInferredWithoutBackup() throws URISyntaxException, IOException { Mockito.when(mockProjectProperties.getMainClassFromJar()).thenReturn(null); - Mockito.when(mockProjectProperties.getJavaLayerConfigurations().getClassLayerEntries()) + Mockito.when(mockProjectProperties.getClassFiles()) .thenReturn( new DirectoryWalker( Paths.get(Resources.getResource("core/class-finder-tests/multiple").toURI())) .walk() - .stream() - .map(path -> new LayerEntry(path, AbsoluteUnixPath.get("/ignored"), null)) - .collect(ImmutableList.toImmutableList())); + .asList()); try { MainClassResolver.resolveMainClass(null, mockProjectProperties); Assert.fail(); @@ -124,12 +112,11 @@ public void testResolveMainClass_multipleInferredWithoutBackup() } @Test - public void testResolveMainClass_noneInferredWithBackup() throws MainClassInferenceException { + public void testResolveMainClass_noneInferredWithBackup() + throws MainClassInferenceException, IOException { Mockito.when(mockProjectProperties.getMainClassFromJar()).thenReturn("${start-class}"); - Mockito.when(mockProjectProperties.getJavaLayerConfigurations().getClassLayerEntries()) - .thenReturn( - ImmutableList.of( - new LayerEntry(Paths.get("ignored"), AbsoluteUnixPath.get("/ignored"), null))); + Mockito.when(mockProjectProperties.getClassFiles()) + .thenReturn(ImmutableList.of(Paths.get("ignored"))); Assert.assertEquals( "${start-class}", MainClassResolver.resolveMainClass(null, mockProjectProperties)); Mockito.verify(mockJibEventConsumer) @@ -137,11 +124,9 @@ public void testResolveMainClass_noneInferredWithBackup() throws MainClassInfere } @Test - public void testResolveMainClass_noneInferredWithoutBackup() { - Mockito.when(mockJavaLayerConfigurations.getClassLayerEntries()) - .thenReturn( - ImmutableList.of( - new LayerEntry(Paths.get("ignored"), AbsoluteUnixPath.get("/ignored"), null))); + public void testResolveMainClass_noneInferredWithoutBackup() throws IOException { + Mockito.when(mockProjectProperties.getClassFiles()) + .thenReturn(ImmutableList.of(Paths.get("ignored"))); try { MainClassResolver.resolveMainClass(null, mockProjectProperties); Assert.fail(); diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java index 67b68bd349..1fa3dc6b0d 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java @@ -17,6 +17,7 @@ package com.google.cloud.tools.jib.plugins.common; import com.google.cloud.tools.jib.api.Containerizer; +import com.google.cloud.tools.jib.api.Jib; import com.google.cloud.tools.jib.api.JibContainerBuilder; import com.google.cloud.tools.jib.api.JibContainerBuilderTestHelper; import com.google.cloud.tools.jib.api.RegistryImage; @@ -64,18 +65,20 @@ private static BuildConfiguration getBuildConfiguration(JibContainerBuilder jibC @Mock private Consumer logger; @Before - public void setUp() { + public void setUp() throws IOException, InvalidImageReferenceException { Mockito.when(rawConfiguration.getFromAuth()).thenReturn(authProperty); Mockito.when(rawConfiguration.getEntrypoint()).thenReturn(Optional.empty()); Mockito.when(rawConfiguration.getAppRoot()).thenReturn("/app"); Mockito.when(projectProperties.getToolName()).thenReturn("tool"); - Mockito.when(projectProperties.getJavaLayerConfigurations()) - .thenReturn(JavaLayerConfigurations.builder().build()); Mockito.when(projectProperties.getMainClassFromJar()).thenReturn("java.lang.Object"); Mockito.when(projectProperties.getEventHandlers()) .thenReturn(new EventHandlers().add(JibEventType.LOGGING, logger)); Mockito.when(projectProperties.getDefaultCacheDirectory()).thenReturn(Paths.get("cache")); + Mockito.when(projectProperties.getContainerBuilderWithLayers(Mockito.any())) + .thenReturn( + Jib.from("base") + .setLayers(JavaLayerConfigurations.builder().build().getLayerConfigurations())); Mockito.when(containerizer.setToolName(Mockito.anyString())).thenReturn(containerizer); Mockito.when(containerizer.setEventHandlers(Mockito.any(EventHandlers.class))) @@ -166,7 +169,7 @@ public void testEntrypoint() @Test public void testComputeEntrypoint_inheritKeyword() - throws MainClassInferenceException, InvalidAppRootException { + throws MainClassInferenceException, InvalidAppRootException, IOException { Mockito.when(rawConfiguration.getEntrypoint()) .thenReturn(Optional.of(Collections.singletonList("INHERIT"))); @@ -176,7 +179,7 @@ public void testComputeEntrypoint_inheritKeyword() @Test public void testComputeEntrypoint_inheritKeywordInNonSingletonList() - throws MainClassInferenceException, InvalidAppRootException { + throws MainClassInferenceException, InvalidAppRootException, IOException { Mockito.when(rawConfiguration.getEntrypoint()) .thenReturn(Optional.of(Arrays.asList("INHERIT", ""))); From 8fef152573f87ea9e76247aadc9b3f82a23666e8 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 12:54:24 -0400 Subject: [PATCH 03/20] Don't add empty layers in JavaLayerConfigurations --- .../jib/frontend/JavaLayerConfigurations.java | 24 +++++++++++-------- .../frontend/JavaLayerConfigurationsTest.java | 10 ++++++++ 2 files changed, 24 insertions(+), 10 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java index 8a9dd1f593..8a952d01bd 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java @@ -22,7 +22,6 @@ import com.google.cloud.tools.jib.filesystem.DirectoryWalker; import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.annotations.VisibleForTesting; -import com.google.common.base.Preconditions; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; import java.io.IOException; @@ -68,11 +67,7 @@ public static class Builder { private final Map layerBuilders = new EnumMap<>(LayerType.class); - private Builder() { - for (LayerType layerType : LayerType.values()) { - layerBuilders.put(layerType, LayerConfiguration.builder()); - } - } + private Builder() {} /** * Adds a file to a layer. Only adds the single source file to the exact path in the container @@ -111,8 +106,10 @@ public Builder addFile( Path sourceFile, AbsoluteUnixPath pathInContainer, @Nullable FilePermissions permissions) { - Preconditions.checkNotNull(layerBuilders.get(layerType)) - .addEntry(sourceFile, pathInContainer, permissions); + if (layerBuilders.get(layerType) == null) { + layerBuilders.put(layerType, LayerConfiguration.builder()); + } + layerBuilders.get(layerType).addEntry(sourceFile, pathInContainer, permissions); return this; } @@ -167,7 +164,11 @@ public Builder addDirectoryContents( AbsoluteUnixPath basePathInContainer, Map permissionsMap) throws IOException { - LayerConfiguration.Builder builder = Preconditions.checkNotNull(layerBuilders.get(layerType)); + + if (layerBuilders.get(layerType) == null) { + layerBuilders.put(layerType, LayerConfiguration.builder()); + } + LayerConfiguration.Builder builder = layerBuilders.get(layerType); new DirectoryWalker(sourceRoot) .filterRoot() @@ -240,6 +241,9 @@ public ImmutableList getExtraFilesLayerEntries() { } private ImmutableList getLayerEntries(LayerType layerType) { - return Preconditions.checkNotNull(layerConfigurationMap.get(layerType)).getLayerEntries(); + if (layerConfigurationMap.get(layerType) == null) { + return ImmutableList.of(); + } + return layerConfigurationMap.get(layerType).getLayerEntries(); } } diff --git a/jib-core/src/test/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurationsTest.java b/jib-core/src/test/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurationsTest.java index 6b87188412..520bffb1eb 100644 --- a/jib-core/src/test/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurationsTest.java +++ b/jib-core/src/test/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurationsTest.java @@ -264,6 +264,11 @@ public void testAddDirectoryContents_file() throws IOException { Collections.singletonList( new LayerEntry(sourceRoot.resolve("file"), basePath.resolve("file"), null)), configurations.getExtraFilesLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getClassLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getResourceLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getDependencyLayerEntries()); + Assert.assertEquals( + Collections.emptyList(), configurations.getSnapshotDependencyLayerEntries()); } @Test @@ -281,6 +286,11 @@ public void testAddDirectoryContents_emptyDirectory() throws IOException { Collections.singletonList( new LayerEntry(sourceRoot.resolve("leaf"), basePath.resolve("leaf"), null)), configurations.getClassLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getResourceLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getDependencyLayerEntries()); + Assert.assertEquals( + Collections.emptyList(), configurations.getSnapshotDependencyLayerEntries()); + Assert.assertEquals(Collections.emptyList(), configurations.getExtraFilesLayerEntries()); } @Test From dcf73194315b4f1f38edd3ea0892e579edb6807f Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 13:59:42 -0400 Subject: [PATCH 04/20] Remove newline --- .../google/cloud/tools/jib/frontend/JavaLayerConfigurations.java | 1 - 1 file changed, 1 deletion(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java index 8a952d01bd..1e11ff8922 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/JavaLayerConfigurations.java @@ -164,7 +164,6 @@ public Builder addDirectoryContents( AbsoluteUnixPath basePathInContainer, Map permissionsMap) throws IOException { - if (layerBuilders.get(layerType) == null) { layerBuilders.put(layerType, LayerConfiguration.builder()); } From ae1320d2541e227c02e4e85bcb55b9b9d0b4b0ea Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 14:52:41 -0400 Subject: [PATCH 05/20] Move tests around --- .../jib/gradle/GradleProjectProperties.java | 6 +- .../gradle/GradleLayerConfigurationsTest.java | 530 ------------------ .../gradle/GradleProjectPropertiesTest.java | 483 +++++++++++++++- .../maven/MavenLayerConfigurationsTest.java | 392 ------------- .../jib/maven/MavenProjectPropertiesTest.java | 365 +++++++++++- 5 files changed, 845 insertions(+), 931 deletions(-) delete mode 100644 jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurationsTest.java delete mode 100644 jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurationsTest.java diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index e79b849c04..cfd07d2fc4 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -26,7 +26,7 @@ import com.google.cloud.tools.jib.event.progress.ProgressEventHandler; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.filesystem.DirectoryWalker; -import com.google.cloud.tools.jib.plugins.common.JavaLayerConfigurationsHelper; +import com.google.cloud.tools.jib.plugins.common.JavaContainerBuilderHelper; import com.google.cloud.tools.jib.plugins.common.ProjectProperties; import com.google.cloud.tools.jib.plugins.common.PropertyNames; import com.google.cloud.tools.jib.plugins.common.TimerEventHandler; @@ -177,7 +177,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage if (TaskCommon.getWarTask(project) != null) { logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); Path explodedWarPath = GradleProjectProperties.getExplodedWarDirectory(project); - return JavaLayerConfigurationsHelper.fromExplodedWar( + return JavaContainerBuilderHelper.fromExplodedWar( baseImage, explodedWarPath, appRoot, extraDirectory, permissions); } @@ -225,7 +225,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage // Adds all the extra files. if (Files.exists(extraDirectory)) { jibContainerBuilder.addLayer( - JavaLayerConfigurationsHelper.extraDirectoryLayerConfiguration( + JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( extraDirectory, permissions)); } return jibContainerBuilder; diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurationsTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurationsTest.java deleted file mode 100644 index 35ad7a5be4..0000000000 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleLayerConfigurationsTest.java +++ /dev/null @@ -1,530 +0,0 @@ -/* - * Copyright 2018 Google LLC. - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations under - * the License. - */ - -package com.google.cloud.tools.jib.gradle; - -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.image.LayerEntry; -import com.google.common.collect.ImmutableList; -import com.google.common.collect.ImmutableSet; -import com.google.common.io.Resources; -import java.io.File; -import java.io.IOException; -import java.net.URISyntaxException; -import java.nio.file.Files; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.util.Arrays; -import java.util.Collections; -import java.util.HashSet; -import java.util.List; -import java.util.Set; -import java.util.function.Function; -import java.util.stream.Collectors; -import org.gradle.api.Project; -import org.gradle.api.Task; -import org.gradle.api.file.FileCollection; -import org.gradle.api.internal.file.AbstractFileCollection; -import org.gradle.api.logging.Logger; -import org.gradle.api.plugins.Convention; -import org.gradle.api.plugins.JavaPluginConvention; -import org.gradle.api.plugins.WarPluginConvention; -import org.gradle.api.tasks.SourceSet; -import org.gradle.api.tasks.SourceSetContainer; -import org.gradle.api.tasks.SourceSetOutput; -import org.gradle.api.tasks.TaskContainer; -import org.gradle.api.tasks.TaskDependency; -import org.gradle.api.tasks.bundling.War; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Rule; -import org.junit.Test; -import org.junit.rules.TemporaryFolder; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.Mockito; -import org.mockito.junit.MockitoJUnitRunner; - -/** Test for {@link GradleLayerConfigurations}. */ -@RunWith(MockitoJUnitRunner.class) -public class GradleLayerConfigurationsTest { - - /** Implementation of {@link FileCollection} that just holds a set of {@link File}s. */ - private static class TestFileCollection extends AbstractFileCollection { - - private final Set files; - - private TestFileCollection(Set files) { - this.files = files.stream().map(Path::toFile).collect(Collectors.toSet()); - } - - @Override - public String getDisplayName() { - return null; - } - - @Override - public Set getFiles() { - return files; - } - - @Override - public TaskDependency getBuildDependencies() { - return new TaskDependency() { - - @Override - public Set getDependencies(Task task) { - return Collections.emptySet(); - } - }; - } - } - - private static void assertLayerEntriesUnordered( - List expectedPaths, List entries, Function fieldSelector) { - List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); - List actual = entries.stream().map(fieldSelector).sorted().collect(Collectors.toList()); - Assert.assertEquals(expected, actual); - } - - private static void assertSourcePathsUnordered( - List expectedPaths, List entries) { - assertLayerEntriesUnordered(expectedPaths, entries, LayerEntry::getSourceFile); - } - - private static void assertExtractionPathsUnordered( - List expectedPaths, List entries) { - assertLayerEntriesUnordered( - expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); - } - - @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); - - @Mock private Project mockProject; - @Mock private Project mockWebAppProject; - @Mock private Convention mockConvention; - @Mock private JavaPluginConvention mockJavaPluginConvention; - @Mock private WarPluginConvention mockWarPluginConvention; - @Mock private SourceSetContainer mockSourceSetContainer; - @Mock private SourceSet mockMainSourceSet; - @Mock private SourceSetOutput mockMainSourceSetOutput; - @Mock private Logger mockLogger; - @Mock private TaskContainer taskContainer; - @Mock private War war; - - private Path extraFilesDirectory; - - @Before - public void setUp() throws URISyntaxException, IOException { - Set classesFiles = - ImmutableSet.of(Paths.get(Resources.getResource("gradle/application/classes").toURI())); - FileCollection classesFileCollection = new TestFileCollection(classesFiles); - Path resourcesOutputDir = - Paths.get(Resources.getResource("gradle/application/resources").toURI()); - - Set allFiles = new HashSet<>(classesFiles); - allFiles.add(resourcesOutputDir); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/library.jarC.jar").toURI())); - allFiles.add( - Paths.get(Resources.getResource("gradle/application/dependencies/libraryB.jar").toURI())); - allFiles.add( - Paths.get(Resources.getResource("gradle/application/dependencies/libraryA.jar").toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/dependency-1.0.0.jar").toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/more/dependency-1.0.0.jar") - .toURI())); - allFiles.add( - Paths.get( - Resources.getResource( - "gradle/application/dependencies/another/one/dependency-1.0.0.jar") - .toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/dependencyX-1.0.0-SNAPSHOT.jar") - .toURI())); - FileCollection runtimeFileCollection = new TestFileCollection(allFiles); - - Mockito.when(mockProject.getConvention()).thenReturn(mockConvention); - Mockito.when(mockConvention.getPlugin(JavaPluginConvention.class)) - .thenReturn(mockJavaPluginConvention); - Mockito.when(mockJavaPluginConvention.getSourceSets()).thenReturn(mockSourceSetContainer); - Mockito.when(mockSourceSetContainer.getByName("main")).thenReturn(mockMainSourceSet); - Mockito.when(mockMainSourceSet.getOutput()).thenReturn(mockMainSourceSetOutput); - Mockito.when(mockMainSourceSetOutput.getClassesDirs()).thenReturn(classesFileCollection); - Mockito.when(mockMainSourceSetOutput.getResourcesDir()).thenReturn(resourcesOutputDir.toFile()); - Mockito.when(mockMainSourceSet.getRuntimeClasspath()).thenReturn(runtimeFileCollection); - // We can't commit an empty directory in Git, so create (if not exist). - Path emptyDirectory = - Paths.get(Resources.getResource("gradle/webapp").toURI()) - .resolve("jib-exploded-war/WEB-INF/classes/empty_dir"); - Files.createDirectories(emptyDirectory); - - extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); - } - - @Test - public void test_correctFiles() throws URISyntaxException, IOException { - Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); - ImmutableList expectedDependenciesFiles = - ImmutableList.of( - applicationDirectory.resolve("dependencies/dependency-1.0.0.jar"), - applicationDirectory.resolve("dependencies/more/dependency-1.0.0.jar"), - applicationDirectory.resolve("dependencies/another/one/dependency-1.0.0.jar"), - applicationDirectory.resolve("dependencies/libraryA.jar"), - applicationDirectory.resolve("dependencies/libraryB.jar"), - applicationDirectory.resolve("dependencies/library.jarC.jar")); - ImmutableList expectedSnapshotDependenciesFiles = - ImmutableList.of( - applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = - ImmutableList.of( - applicationDirectory.resolve("resources/resourceA"), - applicationDirectory.resolve("resources/resourceB"), - applicationDirectory.resolve("resources/world")); - ImmutableList expectedClassesFiles = - ImmutableList.of( - applicationDirectory.resolve("classes/HelloWorld.class"), - applicationDirectory.resolve("classes/some.class")); - ImmutableList expectedExtraFiles = ImmutableList.of(); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - JavaLayerConfigurations javaLayerConfigurations = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - appRoot); - assertSourcePathsUnordered( - expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, - javaLayerConfigurations.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); - assertSourcePathsUnordered( - expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); - assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); - } - - @Test - public void test_noClassesFiles() throws IOException { - Path nonexistentFile = Paths.get("/nonexistent/file"); - Mockito.when(mockMainSourceSetOutput.getClassesDirs()) - .thenReturn(new TestFileCollection(ImmutableSet.of(nonexistentFile))); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - GradleLayerConfigurations.getForProject( - mockProject, mockLogger, Paths.get("nonexistent/path"), Collections.emptyMap(), appRoot); - - Mockito.verify(mockLogger) - .info("Adding corresponding output directories of source sets to image"); - Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); - Mockito.verify(mockLogger).warn("No classes files were found - did you compile your project?"); - } - - @Test - public void test_missingDependencyFiles() throws IOException { - Path nonexistentFile = Paths.get("/nonexistent/dependency"); - FileCollection runtimeFileCollection = - new TestFileCollection(Collections.singleton(nonexistentFile)); - Mockito.when(mockMainSourceSet.getRuntimeClasspath()).thenReturn(runtimeFileCollection); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - GradleLayerConfigurations.getForProject( - mockProject, mockLogger, extraFilesDirectory, Collections.emptyMap(), appRoot); - - Mockito.verify(mockLogger) - .info("Adding corresponding output directories of source sets to image"); - Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); - } - - @Test - public void test_extraFiles() throws IOException { - JavaLayerConfigurations javaLayerConfigurations = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")); - - ImmutableList expectedExtraFiles = - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); - } - - @Test - public void testGetForProject_nonDefaultAppRoot() throws IOException { - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")); - - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/libs/dependency-1.0.0-770.jar", - "/my/app/libs/dependency-1.0.0-200.jar", - "/my/app/libs/dependency-1.0.0-480.jar", - "/my/app/libs/libraryA.jar", - "/my/app/libs/libraryB.jar", - "/my/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/resources/resourceA", - "/my/app/resources/resourceB", - "/my/app/resources/world"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Test - public void testGetForProject_defaultAppRoot() throws IOException { - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_APP_ROOT)); - - assertExtractionPathsUnordered( - Arrays.asList( - "/app/libs/dependency-1.0.0-770.jar", - "/app/libs/dependency-1.0.0-200.jar", - "/app/libs/dependency-1.0.0-480.jar", - "/app/libs/libraryA.jar", - "/app/libs/libraryB.jar", - "/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/app/resources/resourceA", "/app/resources/resourceB", "/app/resources/world"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Test - public void testWebApp() throws URISyntaxException, IOException { - Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); - setUpWarProject(webAppDirectory); - - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")); - ImmutableList expectedDependenciesFiles = - ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")); - ImmutableList expectedSnapshotDependenciesFiles = - ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = - ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/META-INF"), - webAppDirectory.resolve("jib-exploded-war/META-INF/context.xml"), - webAppDirectory.resolve("jib-exploded-war/Test.jsp"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/test.properties"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")); - ImmutableList expectedClassesFiles = - ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/HelloWorld.class"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")); - ImmutableList expectedExtraFiles = - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedDependenciesFiles, configuration.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); - assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); - assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); - - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/META-INF", - "/my/app/META-INF/context.xml", - "/my/app/Test.jsp", - "/my/app/WEB-INF", - "/my/app/WEB-INF/classes", - "/my/app/WEB-INF/classes/empty_dir", - "/my/app/WEB-INF/classes/package", - "/my/app/WEB-INF/classes/package/test.properties", - "/my/app/WEB-INF/lib", - "/my/app/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/WEB-INF/classes/HelloWorld.class", - "/my/app/WEB-INF/classes/empty_dir", - "/my/app/WEB-INF/classes/package", - "/my/app/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Test - public void testWebApp_defaultWebAppRoot() throws URISyntaxException, IOException { - setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); - - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); - - assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/jetty/webapps/ROOT/META-INF", - "/jetty/webapps/ROOT/META-INF/context.xml", - "/jetty/webapps/ROOT/Test.jsp", - "/jetty/webapps/ROOT/WEB-INF", - "/jetty/webapps/ROOT/WEB-INF/classes", - "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", - "/jetty/webapps/ROOT/WEB-INF/classes/package", - "/jetty/webapps/ROOT/WEB-INF/classes/package/test.properties", - "/jetty/webapps/ROOT/WEB-INF/lib", - "/jetty/webapps/ROOT/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/jetty/webapps/ROOT/WEB-INF/classes/HelloWorld.class", - "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", - "/jetty/webapps/ROOT/WEB-INF/classes/package", - "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { - temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); - setUpWarProject(temporaryFolder.getRoot().toPath()); - - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass - } - - @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { - temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); - setUpWarProject(temporaryFolder.getRoot().toPath()); - - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass - } - - @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { - temporaryFolder.newFolder("jib-exploded-war"); - setUpWarProject(temporaryFolder.getRoot().toPath()); - - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass - } - - private void setUpWarProject(Path webAppDirectory) { - Mockito.when(mockWebAppProject.getBuildDir()).thenReturn(webAppDirectory.toFile()); - Mockito.when(mockWebAppProject.getConvention()).thenReturn(mockConvention); - Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)) - .thenReturn(mockWarPluginConvention); - Mockito.when(mockWarPluginConvention.getProject()).thenReturn(mockWebAppProject); - Mockito.when(mockWebAppProject.getTasks()).thenReturn(taskContainer); - Mockito.when(taskContainer.findByName("war")).thenReturn(war); - } -} diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index a5e0eaaa39..520b6cd65f 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -19,12 +19,29 @@ import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.image.LayerEntry; +import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; +import com.google.common.io.Resources; +import java.io.File; +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.Arrays; import java.util.Collections; +import java.util.HashSet; +import java.util.List; +import java.util.Set; +import java.util.function.Function; +import java.util.stream.Collectors; import org.gradle.StartParameter; import org.gradle.api.JavaVersion; import org.gradle.api.Project; +import org.gradle.api.file.FileCollection; +import org.gradle.api.internal.file.AbstractFileCollection; import org.gradle.api.internal.file.FileResolver; import org.gradle.api.invocation.Gradle; import org.gradle.api.java.archives.Manifest; @@ -34,14 +51,20 @@ import org.gradle.api.plugins.Convention; import org.gradle.api.plugins.JavaPluginConvention; import org.gradle.api.plugins.WarPluginConvention; +import org.gradle.api.tasks.SourceSet; +import org.gradle.api.tasks.SourceSetContainer; +import org.gradle.api.tasks.SourceSetOutput; import org.gradle.api.tasks.TaskContainer; +import org.gradle.api.tasks.TaskDependency; import org.gradle.api.tasks.bundling.War; import org.gradle.jvm.tasks.Jar; import org.hamcrest.CoreMatchers; import org.junit.Assert; import org.junit.Assume; import org.junit.Before; +import org.junit.Rule; import org.junit.Test; +import org.junit.rules.TemporaryFolder; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.Mockito; @@ -51,6 +74,51 @@ @RunWith(MockitoJUnitRunner.class) public class GradleProjectPropertiesTest { + /** Implementation of {@link FileCollection} that just holds a set of {@link File}s. */ + private static class TestFileCollection extends AbstractFileCollection { + + private final Set files; + + private TestFileCollection(Set files) { + this.files = files.stream().map(Path::toFile).collect(Collectors.toSet()); + } + + @Override + public String getDisplayName() { + return null; + } + + @Override + public Set getFiles() { + return files; + } + + @Override + public TaskDependency getBuildDependencies() { + return task -> Collections.emptySet(); + } + } + + private static void assertLayerEntriesUnordered( + List expectedPaths, List entries, Function fieldSelector) { + List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); + List actual = entries.stream().map(fieldSelector).sorted().collect(Collectors.toList()); + Assert.assertEquals(expected, actual); + } + + private static void assertSourcePathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered(expectedPaths, entries, LayerEntry::getSourceFile); + } + + private static void assertExtractionPathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered( + expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); + } + + @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); + @Mock private FileResolver mockFileResolver; @Mock private Jar mockJar; @Mock private Jar mockJar2; @@ -58,19 +126,30 @@ public class GradleProjectPropertiesTest { @Mock private Convention mockConvention; @Mock private WarPluginConvention mockWarPluginConvection; @Mock private TaskContainer mockTaskContainer; - @Mock private JavaLayerConfigurations mockJavaLayerConfigurations; @Mock private Logger mockLogger; @Mock private Gradle mockGradle; @Mock private StartParameter mockStartParameter; @Mock private JavaPluginConvention mockJavaPluginConvention; + @Mock private Project mockWebAppProject; + @Mock private WarPluginConvention mockWarPluginConvention; + @Mock private SourceSetContainer mockSourceSetContainer; + @Mock private SourceSet mockMainSourceSet; + @Mock private SourceSetOutput mockMainSourceSetOutput; + @Mock private TaskContainer taskContainer; + @Mock private War war; + + private Path extraFilesDirectory; private Manifest manifest; private GradleProjectProperties gradleProjectProperties; @Before - public void setup() { + public void setup() throws URISyntaxException, IOException { manifest = new DefaultManifest(mockFileResolver); Mockito.when(mockProject.getConvention()).thenReturn(mockConvention); + Mockito.when(mockConvention.getPlugin(JavaPluginConvention.class)) + .thenReturn(mockJavaPluginConvention); + Mockito.when(mockJavaPluginConvention.getSourceSets()).thenReturn(mockSourceSetContainer); Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)) .thenReturn(mockWarPluginConvection); Mockito.when(mockWarPluginConvection.getProject()).thenReturn(mockProject); @@ -82,8 +161,59 @@ public void setup() { Mockito.when(mockGradle.getStartParameter()).thenReturn(mockStartParameter); Mockito.when(mockStartParameter.getConsoleOutput()).thenReturn(ConsoleOutput.Auto); + Set classesFiles = + ImmutableSet.of(Paths.get(Resources.getResource("gradle/application/classes").toURI())); + FileCollection classesFileCollection = new TestFileCollection(classesFiles); + Path resourcesOutputDir = + Paths.get(Resources.getResource("gradle/application/resources").toURI()); + + Set allFiles = new HashSet<>(classesFiles); + allFiles.add(resourcesOutputDir); + allFiles.add( + Paths.get( + Resources.getResource("gradle/application/dependencies/library.jarC.jar").toURI())); + allFiles.add( + Paths.get(Resources.getResource("gradle/application/dependencies/libraryB.jar").toURI())); + allFiles.add( + Paths.get(Resources.getResource("gradle/application/dependencies/libraryA.jar").toURI())); + allFiles.add( + Paths.get( + Resources.getResource("gradle/application/dependencies/dependency-1.0.0.jar").toURI())); + allFiles.add( + Paths.get( + Resources.getResource("gradle/application/dependencies/more/dependency-1.0.0.jar") + .toURI())); + allFiles.add( + Paths.get( + Resources.getResource( + "gradle/application/dependencies/another/one/dependency-1.0.0.jar") + .toURI())); + allFiles.add( + Paths.get( + Resources.getResource("gradle/application/dependencies/dependencyX-1.0.0-SNAPSHOT.jar") + .toURI())); + FileCollection runtimeFileCollection = new TestFileCollection(allFiles); + Mockito.when(mockSourceSetContainer.getByName("main")).thenReturn(mockMainSourceSet); + Mockito.when(mockMainSourceSet.getOutput()).thenReturn(mockMainSourceSetOutput); + Mockito.when(mockMainSourceSetOutput.getClassesDirs()).thenReturn(classesFileCollection); + Mockito.when(mockMainSourceSetOutput.getResourcesDir()).thenReturn(resourcesOutputDir.toFile()); + Mockito.when(mockMainSourceSet.getRuntimeClasspath()).thenReturn(runtimeFileCollection); + + // We can't commit an empty directory in Git, so create (if not exist). + Path emptyDirectory = + Paths.get(Resources.getResource("gradle/webapp").toURI()) + .resolve("jib-exploded-war/WEB-INF/classes/empty_dir"); + Files.createDirectories(emptyDirectory); + + extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + gradleProjectProperties = - new GradleProjectProperties(mockProject, mockLogger, mockJavaLayerConfigurations); + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + ImmutableMap.of(), + AbsoluteUnixPath.get("/app")); } @Test @@ -182,4 +312,351 @@ public void testGetMajorJavaVersion_jvm11() { Assert.assertEquals(11, gradleProjectProperties.getMajorJavaVersion()); } + + @Test + public void test_correctFiles() throws URISyntaxException, IOException { + Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); + ImmutableList expectedDependenciesFiles = + ImmutableList.of( + applicationDirectory.resolve("dependencies/dependency-1.0.0.jar"), + applicationDirectory.resolve("dependencies/more/dependency-1.0.0.jar"), + applicationDirectory.resolve("dependencies/another/one/dependency-1.0.0.jar"), + applicationDirectory.resolve("dependencies/libraryA.jar"), + applicationDirectory.resolve("dependencies/libraryB.jar"), + applicationDirectory.resolve("dependencies/library.jarC.jar")); + ImmutableList expectedSnapshotDependenciesFiles = + ImmutableList.of( + applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")); + ImmutableList expectedResourcesFiles = + ImmutableList.of( + applicationDirectory.resolve("resources/resourceA"), + applicationDirectory.resolve("resources/resourceB"), + applicationDirectory.resolve("resources/world")); + ImmutableList expectedClassesFiles = + ImmutableList.of( + applicationDirectory.resolve("classes/HelloWorld.class"), + applicationDirectory.resolve("classes/some.class")); + ImmutableList expectedExtraFiles = ImmutableList.of(); + + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); + JavaLayerConfigurations javaLayerConfigurations = + GradleLayerConfigurations.getForProject( + mockProject, + mockLogger, + Paths.get("nonexistent/path"), + Collections.emptyMap(), + appRoot); + assertSourcePathsUnordered( + expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedSnapshotDependenciesFiles, + javaLayerConfigurations.getSnapshotDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); + assertSourcePathsUnordered( + expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); + assertSourcePathsUnordered( + expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + } + + @Test + public void test_noClassesFiles() throws IOException { + Path nonexistentFile = Paths.get("/nonexistent/file"); + Mockito.when(mockMainSourceSetOutput.getClassesDirs()) + .thenReturn(new TestFileCollection(ImmutableSet.of(nonexistentFile))); + + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); + GradleLayerConfigurations.getForProject( + mockProject, mockLogger, Paths.get("nonexistent/path"), Collections.emptyMap(), appRoot); + + Mockito.verify(mockLogger) + .info("Adding corresponding output directories of source sets to image"); + Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); + Mockito.verify(mockLogger).warn("No classes files were found - did you compile your project?"); + } + + @Test + public void test_missingDependencyFiles() throws IOException { + Path nonexistentFile = Paths.get("/nonexistent/dependency"); + FileCollection runtimeFileCollection = + new TestFileCollection(Collections.singleton(nonexistentFile)); + Mockito.when(mockMainSourceSet.getRuntimeClasspath()).thenReturn(runtimeFileCollection); + + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); + GradleLayerConfigurations.getForProject( + mockProject, mockLogger, extraFilesDirectory, Collections.emptyMap(), appRoot); + + Mockito.verify(mockLogger) + .info("Adding corresponding output directories of source sets to image"); + Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); + } + + @Test + public void test_extraFiles() throws IOException { + JavaLayerConfigurations javaLayerConfigurations = + GradleLayerConfigurations.getForProject( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")); + + ImmutableList expectedExtraFiles = + ImmutableList.of( + extraFilesDirectory.resolve("a"), + extraFilesDirectory.resolve("a/b"), + extraFilesDirectory.resolve("a/b/bar"), + extraFilesDirectory.resolve("c"), + extraFilesDirectory.resolve("c/cat"), + extraFilesDirectory.resolve("foo")); + + assertSourcePathsUnordered( + expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + } + + @Test + public void testGetForProject_nonDefaultAppRoot() throws IOException { + JavaLayerConfigurations configuration = + GradleLayerConfigurations.getForProject( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")); + + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/libs/dependency-1.0.0-770.jar", + "/my/app/libs/dependency-1.0.0-200.jar", + "/my/app/libs/dependency-1.0.0-480.jar", + "/my/app/libs/libraryA.jar", + "/my/app/libs/libraryB.jar", + "/my/app/libs/library.jarC.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/resources/resourceA", + "/my/app/resources/resourceB", + "/my/app/resources/world"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Test + public void testGetForProject_defaultAppRoot() throws IOException { + JavaLayerConfigurations configuration = + GradleLayerConfigurations.getForProject( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_APP_ROOT)); + + assertExtractionPathsUnordered( + Arrays.asList( + "/app/libs/dependency-1.0.0-770.jar", + "/app/libs/dependency-1.0.0-200.jar", + "/app/libs/dependency-1.0.0-480.jar", + "/app/libs/libraryA.jar", + "/app/libs/libraryB.jar", + "/app/libs/library.jarC.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/app/resources/resourceA", "/app/resources/resourceB", "/app/resources/world"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Test + public void testWebApp() throws URISyntaxException, IOException { + Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); + setUpWarProject(webAppDirectory); + + JavaLayerConfigurations configuration = + GradleLayerConfigurations.getForProject( + mockWebAppProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")); + ImmutableList expectedDependenciesFiles = + ImmutableList.of( + webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")); + ImmutableList expectedSnapshotDependenciesFiles = + ImmutableList.of( + webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); + ImmutableList expectedResourcesFiles = + ImmutableList.of( + webAppDirectory.resolve("jib-exploded-war/META-INF"), + webAppDirectory.resolve("jib-exploded-war/META-INF/context.xml"), + webAppDirectory.resolve("jib-exploded-war/Test.jsp"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/test.properties"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")); + ImmutableList expectedClassesFiles = + ImmutableList.of( + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/HelloWorld.class"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")); + ImmutableList expectedExtraFiles = + ImmutableList.of( + extraFilesDirectory.resolve("a"), + extraFilesDirectory.resolve("a/b"), + extraFilesDirectory.resolve("a/b/bar"), + extraFilesDirectory.resolve("c"), + extraFilesDirectory.resolve("c/cat"), + extraFilesDirectory.resolve("foo")); + + assertSourcePathsUnordered( + expectedDependenciesFiles, configuration.getDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); + assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); + assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); + assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); + + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/META-INF", + "/my/app/META-INF/context.xml", + "/my/app/Test.jsp", + "/my/app/WEB-INF", + "/my/app/WEB-INF/classes", + "/my/app/WEB-INF/classes/empty_dir", + "/my/app/WEB-INF/classes/package", + "/my/app/WEB-INF/classes/package/test.properties", + "/my/app/WEB-INF/lib", + "/my/app/WEB-INF/web.xml"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/WEB-INF/classes/HelloWorld.class", + "/my/app/WEB-INF/classes/empty_dir", + "/my/app/WEB-INF/classes/package", + "/my/app/WEB-INF/classes/package/Other.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Test + public void testWebApp_defaultWebAppRoot() throws URISyntaxException, IOException { + setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); + + JavaLayerConfigurations configuration = + GradleLayerConfigurations.getForProject( + mockWebAppProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); + + assertExtractionPathsUnordered( + Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/jetty/webapps/ROOT/META-INF", + "/jetty/webapps/ROOT/META-INF/context.xml", + "/jetty/webapps/ROOT/Test.jsp", + "/jetty/webapps/ROOT/WEB-INF", + "/jetty/webapps/ROOT/WEB-INF/classes", + "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", + "/jetty/webapps/ROOT/WEB-INF/classes/package", + "/jetty/webapps/ROOT/WEB-INF/classes/package/test.properties", + "/jetty/webapps/ROOT/WEB-INF/lib", + "/jetty/webapps/ROOT/WEB-INF/web.xml"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/jetty/webapps/ROOT/WEB-INF/classes/HelloWorld.class", + "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", + "/jetty/webapps/ROOT/WEB-INF/classes/package", + "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Test + public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { + temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); + setUpWarProject(temporaryFolder.getRoot().toPath()); + + GradleLayerConfigurations.getForProject( + mockWebAppProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + } + + @Test + public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { + temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); + setUpWarProject(temporaryFolder.getRoot().toPath()); + + GradleLayerConfigurations.getForProject( + mockWebAppProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + } + + @Test + public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { + temporaryFolder.newFolder("jib-exploded-war"); + setUpWarProject(temporaryFolder.getRoot().toPath()); + + GradleLayerConfigurations.getForProject( + mockWebAppProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + } + + private void setUpWarProject(Path webAppDirectory) { + Mockito.when(mockWebAppProject.getBuildDir()).thenReturn(webAppDirectory.toFile()); + Mockito.when(mockWebAppProject.getConvention()).thenReturn(mockConvention); + Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)) + .thenReturn(mockWarPluginConvention); + Mockito.when(mockWarPluginConvention.getProject()).thenReturn(mockWebAppProject); + Mockito.when(mockWebAppProject.getTasks()).thenReturn(taskContainer); + Mockito.when(taskContainer.findByName("war")).thenReturn(war); + } } diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurationsTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurationsTest.java deleted file mode 100644 index 56b0081ec4..0000000000 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenLayerConfigurationsTest.java +++ /dev/null @@ -1,392 +0,0 @@ -/* - * Copyright 2018 Google LLC. - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not - * use this file except in compliance with the License. You may obtain a copy of - * the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations under - * the License. - */ - -package com.google.cloud.tools.jib.maven; - -import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; -import com.google.cloud.tools.jib.image.LayerEntry; -import com.google.common.collect.ImmutableList; -import com.google.common.collect.ImmutableSet; -import com.google.common.io.Resources; -import java.io.IOException; -import java.net.URISyntaxException; -import java.nio.file.Files; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.util.Arrays; -import java.util.Collections; -import java.util.List; -import java.util.Set; -import java.util.function.Function; -import java.util.stream.Collectors; -import org.apache.maven.artifact.Artifact; -import org.apache.maven.model.Build; -import org.apache.maven.project.MavenProject; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Rule; -import org.junit.Test; -import org.junit.rules.TemporaryFolder; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.Mockito; -import org.mockito.junit.MockitoJUnitRunner; - -/** Tests for {@link MavenLayerConfigurations}. */ -@RunWith(MockitoJUnitRunner.class) -public class MavenLayerConfigurationsTest { - - private static void assertLayerEntriesUnordered( - List expectedPaths, List entries, Function fieldSelector) { - List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); - List actual = entries.stream().map(fieldSelector).sorted().collect(Collectors.toList()); - Assert.assertEquals(expected, actual); - } - - private static void assertSourcePathsUnordered( - List expectedPaths, List entries) { - assertLayerEntriesUnordered(expectedPaths, entries, LayerEntry::getSourceFile); - } - - private static void assertExtractionPathsUnordered( - List expectedPaths, List entries) { - assertLayerEntriesUnordered( - expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); - } - - private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuration) { - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/libs/dependency-1.0.0-770.jar", - "/my/app/libs/dependency-1.0.0-200.jar", - "/my/app/libs/dependency-1.0.0-480.jar", - "/my/app/libs/libraryA.jar", - "/my/app/libs/libraryB.jar", - "/my/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/resources/directory", - "/my/app/resources/directory/somefile", - "/my/app/resources/package", - "/my/app/resources/resourceA", - "/my/app/resources/resourceB", - "/my/app/resources/world"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/classes/HelloWorld.class", - "/my/app/classes/directory", - "/my/app/classes/package", - "/my/app/classes/package/some.class", - "/my/app/classes/some.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Rule public final TestRepository testRepository = new TestRepository(); - @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); - - @Mock private MavenProject mockMavenProject; - @Mock private Build mockBuild; - - private Path extraFilesDirectory; - - @Before - public void setUp() throws URISyntaxException, IOException { - Path outputPath = Paths.get(Resources.getResource("maven/application/output").toURI()); - Path dependenciesPath = - Paths.get(Resources.getResource("maven/application/dependencies").toURI()); - - Mockito.when(mockMavenProject.getBuild()).thenReturn(mockBuild); - Mockito.when(mockBuild.getOutputDirectory()).thenReturn(outputPath.toString()); - - Set artifacts = - ImmutableSet.of( - makeArtifact(dependenciesPath.resolve("library.jarC.jar")), - makeArtifact(dependenciesPath.resolve("libraryB.jar")), - makeArtifact(dependenciesPath.resolve("libraryA.jar")), - makeArtifact(dependenciesPath.resolve("more").resolve("dependency-1.0.0.jar")), - makeArtifact( - dependenciesPath.resolve("another").resolve("one").resolve("dependency-1.0.0.jar")), - // Maven reads and populates "Artifacts" with its own processing, so read some from a - // repository - testRepository.findArtifact("com.test", "dependency", "1.0.0"), - testRepository.findArtifact("com.test", "dependencyX", "1.0.0-SNAPSHOT")); - Mockito.when(mockMavenProject.getArtifacts()).thenReturn(artifacts); - - Path emptyDirectory = - Paths.get(Resources.getResource("maven/webapp").toURI()) - .resolve("final-name/WEB-INF/classes/empty_dir"); - Files.createDirectories(emptyDirectory); - - extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); - } - - @Test - public void test_correctFiles() throws URISyntaxException, IOException { - Path dependenciesPath = - Paths.get(Resources.getResource("maven/application/dependencies").toURI()); - ImmutableList expectedDependenciesFiles = - ImmutableList.of( - testRepository.artifactPathOnDisk("com.test", "dependency", "1.0.0"), - dependenciesPath.resolve("more").resolve("dependency-1.0.0.jar"), - dependenciesPath.resolve("another").resolve("one").resolve("dependency-1.0.0.jar"), - dependenciesPath.resolve("libraryA.jar"), - dependenciesPath.resolve("libraryB.jar"), - dependenciesPath.resolve("library.jarC.jar")); - ImmutableList expectedSnapshotDependenciesFiles = - ImmutableList.of( - testRepository.artifactPathOnDisk("com.test", "dependencyX", "1.0.0-SNAPSHOT")); - Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); - ImmutableList expectedResourcesFiles = - ImmutableList.of( - applicationDirectory.resolve("output/directory"), - applicationDirectory.resolve("output/directory/somefile"), - applicationDirectory.resolve("output/package"), - applicationDirectory.resolve("output/resourceA"), - applicationDirectory.resolve("output/resourceB"), - applicationDirectory.resolve("output/world")); - ImmutableList expectedClassesFiles = - ImmutableList.of( - applicationDirectory.resolve("output/HelloWorld.class"), - applicationDirectory.resolve("output/directory"), - applicationDirectory.resolve("output/package"), - applicationDirectory.resolve("output/package/some.class"), - applicationDirectory.resolve("output/some.class")); - - JavaLayerConfigurations javaLayerConfigurations = - MavenLayerConfigurations.getForProject( - mockMavenProject, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")); - assertSourcePathsUnordered( - expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, - javaLayerConfigurations.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); - assertSourcePathsUnordered( - expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); - } - - @Test - public void test_extraFiles() throws IOException { - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - JavaLayerConfigurations javaLayerConfigurations = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); - - ImmutableList expectedExtraFiles = - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); - } - - @Test - public void testGetForProject_nonDefaultAppRoot() throws IOException { - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); - - assertNonDefaultAppRoot(configuration); - } - - private Artifact makeArtifact(Path path) { - Artifact artifact = Mockito.mock(Artifact.class); - Mockito.when(artifact.getFile()).thenReturn(path.toFile()); - return artifact; - } - - @Test - public void testGetForWarProject_nonDefaultAppRoot() throws URISyntaxException, IOException { - Path outputPath = Paths.get(Resources.getResource("maven/webapp").toURI()); - Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - Mockito.when(mockBuild.getDirectory()).thenReturn(outputPath.toString()); - Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); - - ImmutableList expectedDependenciesFiles = - ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")); - ImmutableList expectedSnapshotDependenciesFiles = - ImmutableList.of( - outputPath.resolve("final-name/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = - ImmutableList.of( - outputPath.resolve("final-name/META-INF"), - outputPath.resolve("final-name/META-INF/context.xml"), - outputPath.resolve("final-name/Test.jsp"), - outputPath.resolve("final-name/WEB-INF"), - outputPath.resolve("final-name/WEB-INF/classes"), - outputPath.resolve("final-name/WEB-INF/classes/empty_dir"), - outputPath.resolve("final-name/WEB-INF/classes/package"), - outputPath.resolve("final-name/WEB-INF/classes/package/test.properties"), - outputPath.resolve("final-name/WEB-INF/lib"), - outputPath.resolve("final-name/WEB-INF/web.xml")); - ImmutableList expectedClassesFiles = - ImmutableList.of( - outputPath.resolve("final-name/WEB-INF/classes/HelloWorld.class"), - outputPath.resolve("final-name/WEB-INF/classes/empty_dir"), - outputPath.resolve("final-name/WEB-INF/classes/package"), - outputPath.resolve("final-name/WEB-INF/classes/package/Other.class")); - ImmutableList expectedExtraFiles = - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedDependenciesFiles, configuration.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); - assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); - assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); - - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); - assertExtractionPathsUnordered( - Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/META-INF", - "/my/app/META-INF/context.xml", - "/my/app/Test.jsp", - "/my/app/WEB-INF", - "/my/app/WEB-INF/classes", - "/my/app/WEB-INF/classes/empty_dir", - "/my/app/WEB-INF/classes/package", - "/my/app/WEB-INF/classes/package/test.properties", - "/my/app/WEB-INF/lib", - "/my/app/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList( - "/my/app/WEB-INF/classes/HelloWorld.class", - "/my/app/WEB-INF/classes/empty_dir", - "/my/app/WEB-INF/classes/package", - "/my/app/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); - } - - @Test - public void testGetForJarProject_nonDefaultAppRoot() throws IOException { - // Test when the default packaging is set - Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); - - assertNonDefaultAppRoot(configuration); - } - - @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { - temporaryFolder.newFolder("final-name"); - Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - Mockito.when(mockBuild.getDirectory()) - .thenReturn(temporaryFolder.getRoot().toPath().toString()); - Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass - } - - @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { - temporaryFolder.newFolder("final-name", "WEB-INF", "classes"); - Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - Mockito.when(mockBuild.getDirectory()) - .thenReturn(temporaryFolder.getRoot().toPath().toString()); - Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass - } - - @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { - temporaryFolder.newFolder("final-name", "WEB-INF", "lib"); - Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - Mockito.when(mockBuild.getDirectory()) - .thenReturn(temporaryFolder.getRoot().toPath().toString()); - Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass - } - - @Test - public void testIsWarProject_WarPackagingIsWar() { - Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - - Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); - } - - @Test - public void testIsWarProject_GwtAppPackagingIsWar() { - Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-app"); - - Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); - } - - @Test - public void testIsWarProject_JarPackagingIsNotWar() { - Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - - Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); - } - - @Test - public void testIsWarProject_GwtLibPackagingIsNotWar() { - Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-lib"); - - Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); - } -} diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 4e410b8402..4d7ee62929 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -16,17 +16,38 @@ package com.google.cloud.tools.jib.maven; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.image.LayerEntry; +import com.google.common.collect.ImmutableList; +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.ImmutableSet; +import com.google.common.io.Resources; +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; import java.util.Properties; +import java.util.Set; +import java.util.function.Function; +import java.util.stream.Collectors; +import org.apache.maven.artifact.Artifact; import org.apache.maven.execution.MavenExecutionRequest; import org.apache.maven.execution.MavenSession; +import org.apache.maven.model.Build; import org.apache.maven.model.Plugin; import org.apache.maven.plugin.logging.Log; import org.apache.maven.project.MavenProject; import org.codehaus.plexus.util.xml.Xpp3Dom; import org.junit.Assert; import org.junit.Before; +import org.junit.Rule; import org.junit.Test; +import org.junit.rules.TemporaryFolder; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.Mockito; @@ -36,11 +57,67 @@ @RunWith(MockitoJUnitRunner.class) public class MavenProjectPropertiesTest { + private static void assertLayerEntriesUnordered( + List expectedPaths, List entries, Function fieldSelector) { + List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); + List actual = entries.stream().map(fieldSelector).sorted().collect(Collectors.toList()); + Assert.assertEquals(expected, actual); + } + + private static void assertSourcePathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered(expectedPaths, entries, LayerEntry::getSourceFile); + } + + private static void assertExtractionPathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered( + expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); + } + + private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuration) { + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/libs/dependency-1.0.0-770.jar", + "/my/app/libs/dependency-1.0.0-200.jar", + "/my/app/libs/dependency-1.0.0-480.jar", + "/my/app/libs/libraryA.jar", + "/my/app/libs/libraryB.jar", + "/my/app/libs/library.jarC.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/resources/directory", + "/my/app/resources/directory/somefile", + "/my/app/resources/package", + "/my/app/resources/resourceA", + "/my/app/resources/resourceB", + "/my/app/resources/world"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/classes/HelloWorld.class", + "/my/app/classes/directory", + "/my/app/classes/package", + "/my/app/classes/package/some.class", + "/my/app/classes/some.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Rule public final TestRepository testRepository = new TestRepository(); + @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); + + @Mock private Build mockBuild; @Mock private MavenProject mockMavenProject; @Mock private MavenSession mockMavenSession; @Mock private MavenExecutionRequest mockMavenRequest; @Mock private Properties mockMavenProperties; - @Mock private JavaLayerConfigurations mockJavaLayerConfigurations; @Mock private Plugin mockJarPlugin; @Mock private Plugin mockCompilerPlugin; @Mock private Log mockLog; @@ -55,21 +132,61 @@ public class MavenProjectPropertiesTest { @Mock private Xpp3Dom compilerRelease; private MavenProjectProperties mavenProjectProperties; + private Path extraFilesDirectory; @Before - public void setup() { + public void setup() throws IOException, URISyntaxException { Mockito.when(mockMavenSession.getRequest()).thenReturn(mockMavenRequest); mavenProjectProperties = new MavenProjectProperties( - mockMavenProject, mockMavenSession, mockLog, mockJavaLayerConfigurations); + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + ImmutableMap.of(), + AbsoluteUnixPath.get("/app")); jarPluginConfiguration = new Xpp3Dom(""); archive = new Xpp3Dom("archive"); manifest = new Xpp3Dom("manifest"); jarPluginMainClass = new Xpp3Dom("mainClass"); + Path outputPath = Paths.get(Resources.getResource("maven/application/output").toURI()); + Path dependenciesPath = + Paths.get(Resources.getResource("maven/application/dependencies").toURI()); + + Mockito.when(mockMavenProject.getBuild()).thenReturn(mockBuild); + Mockito.when(mockBuild.getOutputDirectory()).thenReturn(outputPath.toString()); + + Set artifacts = + ImmutableSet.of( + makeArtifact(dependenciesPath.resolve("library.jarC.jar")), + makeArtifact(dependenciesPath.resolve("libraryB.jar")), + makeArtifact(dependenciesPath.resolve("libraryA.jar")), + makeArtifact(dependenciesPath.resolve("more").resolve("dependency-1.0.0.jar")), + makeArtifact( + dependenciesPath.resolve("another").resolve("one").resolve("dependency-1.0.0.jar")), + // Maven reads and populates "Artifacts" with its own processing, so read some from a + // repository + testRepository.findArtifact("com.test", "dependency", "1.0.0"), + testRepository.findArtifact("com.test", "dependencyX", "1.0.0-SNAPSHOT")); + Mockito.when(mockMavenProject.getArtifacts()).thenReturn(artifacts); + + Path emptyDirectory = + Paths.get(Resources.getResource("maven/webapp").toURI()) + .resolve("final-name/WEB-INF/classes/empty_dir"); + Files.createDirectories(emptyDirectory); + + extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + Mockito.when(mockMavenProject.getProperties()).thenReturn(mockMavenProperties); } + private Artifact makeArtifact(Path path) { + Artifact artifact = Mockito.mock(Artifact.class); + Mockito.when(artifact.getFile()).thenReturn(path.toFile()); + return artifact; + } + @Test public void testGetMainClassFromJar_success() { Mockito.when(mockMavenProject.getPlugin("org.apache.maven.plugins:maven-jar-plugin")) @@ -212,4 +329,246 @@ public void isProgressFooterEnabled() { Mockito.when(mockMavenRequest.isInteractiveMode()).thenReturn(false); Assert.assertFalse(MavenProjectProperties.isProgressFooterEnabled(mockMavenSession)); } + + @Test + public void test_correctFiles() throws URISyntaxException, IOException { + Path dependenciesPath = + Paths.get(Resources.getResource("maven/application/dependencies").toURI()); + ImmutableList expectedDependenciesFiles = + ImmutableList.of( + testRepository.artifactPathOnDisk("com.test", "dependency", "1.0.0"), + dependenciesPath.resolve("more").resolve("dependency-1.0.0.jar"), + dependenciesPath.resolve("another").resolve("one").resolve("dependency-1.0.0.jar"), + dependenciesPath.resolve("libraryA.jar"), + dependenciesPath.resolve("libraryB.jar"), + dependenciesPath.resolve("library.jarC.jar")); + ImmutableList expectedSnapshotDependenciesFiles = + ImmutableList.of( + testRepository.artifactPathOnDisk("com.test", "dependencyX", "1.0.0-SNAPSHOT")); + Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); + ImmutableList expectedResourcesFiles = + ImmutableList.of( + applicationDirectory.resolve("output/directory"), + applicationDirectory.resolve("output/directory/somefile"), + applicationDirectory.resolve("output/package"), + applicationDirectory.resolve("output/resourceA"), + applicationDirectory.resolve("output/resourceB"), + applicationDirectory.resolve("output/world")); + ImmutableList expectedClassesFiles = + ImmutableList.of( + applicationDirectory.resolve("output/HelloWorld.class"), + applicationDirectory.resolve("output/directory"), + applicationDirectory.resolve("output/package"), + applicationDirectory.resolve("output/package/some.class"), + applicationDirectory.resolve("output/some.class")); + + JavaLayerConfigurations javaLayerConfigurations = + MavenLayerConfigurations.getForProject( + mockMavenProject, + Paths.get("nonexistent/path"), + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")); + assertSourcePathsUnordered( + expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedSnapshotDependenciesFiles, + javaLayerConfigurations.getSnapshotDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); + assertSourcePathsUnordered( + expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); + } + + @Test + public void test_extraFiles() throws IOException { + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); + JavaLayerConfigurations javaLayerConfigurations = + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + + ImmutableList expectedExtraFiles = + ImmutableList.of( + extraFilesDirectory.resolve("a"), + extraFilesDirectory.resolve("a/b"), + extraFilesDirectory.resolve("a/b/bar"), + extraFilesDirectory.resolve("c"), + extraFilesDirectory.resolve("c/cat"), + extraFilesDirectory.resolve("foo")); + + assertSourcePathsUnordered( + expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + } + + @Test + public void testGetForProject_nonDefaultAppRoot() throws IOException { + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + JavaLayerConfigurations configuration = + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + + assertNonDefaultAppRoot(configuration); + } + + @Test + public void testGetForWarProject_nonDefaultAppRoot() throws URISyntaxException, IOException { + Path outputPath = Paths.get(Resources.getResource("maven/webapp").toURI()); + Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); + Mockito.when(mockBuild.getDirectory()).thenReturn(outputPath.toString()); + Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); + + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + JavaLayerConfigurations configuration = + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + + ImmutableList expectedDependenciesFiles = + ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")); + ImmutableList expectedSnapshotDependenciesFiles = + ImmutableList.of( + outputPath.resolve("final-name/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); + ImmutableList expectedResourcesFiles = + ImmutableList.of( + outputPath.resolve("final-name/META-INF"), + outputPath.resolve("final-name/META-INF/context.xml"), + outputPath.resolve("final-name/Test.jsp"), + outputPath.resolve("final-name/WEB-INF"), + outputPath.resolve("final-name/WEB-INF/classes"), + outputPath.resolve("final-name/WEB-INF/classes/empty_dir"), + outputPath.resolve("final-name/WEB-INF/classes/package"), + outputPath.resolve("final-name/WEB-INF/classes/package/test.properties"), + outputPath.resolve("final-name/WEB-INF/lib"), + outputPath.resolve("final-name/WEB-INF/web.xml")); + ImmutableList expectedClassesFiles = + ImmutableList.of( + outputPath.resolve("final-name/WEB-INF/classes/HelloWorld.class"), + outputPath.resolve("final-name/WEB-INF/classes/empty_dir"), + outputPath.resolve("final-name/WEB-INF/classes/package"), + outputPath.resolve("final-name/WEB-INF/classes/package/Other.class")); + ImmutableList expectedExtraFiles = + ImmutableList.of( + extraFilesDirectory.resolve("a"), + extraFilesDirectory.resolve("a/b"), + extraFilesDirectory.resolve("a/b/bar"), + extraFilesDirectory.resolve("c"), + extraFilesDirectory.resolve("c/cat"), + extraFilesDirectory.resolve("foo")); + + assertSourcePathsUnordered( + expectedDependenciesFiles, configuration.getDependencyLayerEntries()); + assertSourcePathsUnordered( + expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); + assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); + assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); + assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); + + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), + configuration.getDependencyLayerEntries()); + assertExtractionPathsUnordered( + Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), + configuration.getSnapshotDependencyLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/META-INF", + "/my/app/META-INF/context.xml", + "/my/app/Test.jsp", + "/my/app/WEB-INF", + "/my/app/WEB-INF/classes", + "/my/app/WEB-INF/classes/empty_dir", + "/my/app/WEB-INF/classes/package", + "/my/app/WEB-INF/classes/package/test.properties", + "/my/app/WEB-INF/lib", + "/my/app/WEB-INF/web.xml"), + configuration.getResourceLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList( + "/my/app/WEB-INF/classes/HelloWorld.class", + "/my/app/WEB-INF/classes/empty_dir", + "/my/app/WEB-INF/classes/package", + "/my/app/WEB-INF/classes/package/Other.class"), + configuration.getClassLayerEntries()); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), + configuration.getExtraFilesLayerEntries()); + } + + @Test + public void testGetForJarProject_nonDefaultAppRoot() throws IOException { + // Test when the default packaging is set + Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); + + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + JavaLayerConfigurations configuration = + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + + assertNonDefaultAppRoot(configuration); + } + + @Test + public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { + temporaryFolder.newFolder("final-name"); + Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); + Mockito.when(mockBuild.getDirectory()) + .thenReturn(temporaryFolder.getRoot().toPath().toString()); + Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + } + + @Test + public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { + temporaryFolder.newFolder("final-name", "WEB-INF", "classes"); + Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); + Mockito.when(mockBuild.getDirectory()) + .thenReturn(temporaryFolder.getRoot().toPath().toString()); + Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + } + + @Test + public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { + temporaryFolder.newFolder("final-name", "WEB-INF", "lib"); + Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); + Mockito.when(mockBuild.getDirectory()) + .thenReturn(temporaryFolder.getRoot().toPath().toString()); + Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); + AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); + + MavenLayerConfigurations.getForProject( + mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + } + + @Test + public void testIsWarProject_WarPackagingIsWar() { + Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); + + Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); + } + + @Test + public void testIsWarProject_GwtAppPackagingIsWar() { + Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-app"); + + Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); + } + + @Test + public void testIsWarProject_JarPackagingIsNotWar() { + Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); + + Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); + } + + @Test + public void testIsWarProject_GwtLibPackagingIsNotWar() { + Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-lib"); + + Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); + } } From a3c62a0ac661428a24bb924c75b55e3f84fb463b Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 16:34:51 -0400 Subject: [PATCH 06/20] Progress --- .../gradle/GradleProjectPropertiesTest.java | 430 +++++++++++------- 1 file changed, 253 insertions(+), 177 deletions(-) diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index 520b6cd65f..f2032b6c72 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -16,14 +16,22 @@ package com.google.cloud.tools.jib.gradle; +import com.google.cloud.tools.jib.api.Containerizer; +import com.google.cloud.tools.jib.api.RegistryImage; +import com.google.cloud.tools.jib.configuration.BuildConfiguration; +import com.google.cloud.tools.jib.configuration.CacheDirectoryCreationException; import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.configuration.LayerConfiguration; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; +import com.google.cloud.tools.jib.image.InvalidImageReferenceException; import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; import com.google.common.io.Resources; +import com.google.common.util.concurrent.MoreExecutors; import java.io.File; import java.io.IOException; import java.net.URISyntaxException; @@ -117,6 +125,15 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } + private static List getLayerConfigurationByName( + BuildConfiguration buildConfiguration, String name) { + return buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals(name)) + .collect(Collectors.toList()); + } + @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @Mock private FileResolver mockFileResolver; @@ -314,116 +331,122 @@ public void testGetMajorJavaVersion_jvm11() { } @Test - public void test_correctFiles() throws URISyntaxException, IOException { + public void test_correctFiles() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); - ImmutableList expectedDependenciesFiles = + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + Paths.get("nonexistent/path"), + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependency-1.0.0.jar"), applicationDirectory.resolve("dependencies/more/dependency-1.0.0.jar"), applicationDirectory.resolve("dependencies/another/one/dependency-1.0.0.jar"), applicationDirectory.resolve("dependencies/libraryA.jar"), applicationDirectory.resolve("dependencies/libraryB.jar"), - applicationDirectory.resolve("dependencies/library.jarC.jar")); - ImmutableList expectedSnapshotDependenciesFiles = + applicationDirectory.resolve("dependencies/library.jarC.jar")), + dependenciesLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( - applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = + applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), + snapshotsLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("resources/resourceA"), applicationDirectory.resolve("resources/resourceB"), - applicationDirectory.resolve("resources/world")); - ImmutableList expectedClassesFiles = + applicationDirectory.resolve("resources/world")), + resourcesLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("classes/HelloWorld.class"), - applicationDirectory.resolve("classes/some.class")); - ImmutableList expectedExtraFiles = ImmutableList.of(); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - JavaLayerConfigurations javaLayerConfigurations = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - appRoot); - assertSourcePathsUnordered( - expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, - javaLayerConfigurations.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); - assertSourcePathsUnordered( - expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); + applicationDirectory.resolve("classes/some.class")), + classesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + ImmutableList.of(), extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void test_noClassesFiles() throws IOException { + public void test_noClassesFiles() throws InvalidImageReferenceException { Path nonexistentFile = Paths.get("/nonexistent/file"); Mockito.when(mockMainSourceSetOutput.getClassesDirs()) .thenReturn(new TestFileCollection(ImmutableSet.of(nonexistentFile))); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - GradleLayerConfigurations.getForProject( - mockProject, mockLogger, Paths.get("nonexistent/path"), Collections.emptyMap(), appRoot); - - Mockito.verify(mockLogger) - .info("Adding corresponding output directories of source sets to image"); - Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); + gradleProjectProperties.getContainerBuilderWithLayers(RegistryImage.named("base")); Mockito.verify(mockLogger).warn("No classes files were found - did you compile your project?"); } @Test - public void test_missingDependencyFiles() throws IOException { - Path nonexistentFile = Paths.get("/nonexistent/dependency"); - FileCollection runtimeFileCollection = - new TestFileCollection(Collections.singleton(nonexistentFile)); - Mockito.when(mockMainSourceSet.getRuntimeClasspath()).thenReturn(runtimeFileCollection); - - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - GradleLayerConfigurations.getForProject( - mockProject, mockLogger, extraFilesDirectory, Collections.emptyMap(), appRoot); - - Mockito.verify(mockLogger) - .info("Adding corresponding output directories of source sets to image"); - Mockito.verify(mockLogger).info("\t'" + nonexistentFile + "' (not found, skipped)"); - } - - @Test - public void test_extraFiles() throws IOException { - JavaLayerConfigurations javaLayerConfigurations = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")); - - ImmutableList expectedExtraFiles = + public void test_extraFiles() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), extraFilesDirectory.resolve("a/b"), extraFilesDirectory.resolve("a/b/bar"), extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + extraFilesDirectory.resolve("foo")), + extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void testGetForProject_nonDefaultAppRoot() throws IOException { - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")); - + public void testGetForProject_nonDefaultAppRoot() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/libs/dependency-1.0.0-770.jar", @@ -432,34 +455,49 @@ public void testGetForProject_nonDefaultAppRoot() throws IOException { "/my/app/libs/libraryA.jar", "/my/app/libs/libraryB.jar", "/my/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/resources/resourceA", "/my/app/resources/resourceB", "/my/app/resources/world"), - configuration.getResourceLayerEntries()); + resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), - configuration.getClassLayerEntries()); + classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void testGetForProject_defaultAppRoot() throws IOException { - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_APP_ROOT)); - + public void testGetForProject_defaultAppRoot() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_APP_ROOT)) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertExtractionPathsUnordered( Arrays.asList( "/app/libs/dependency-1.0.0-770.jar", @@ -468,41 +506,61 @@ public void testGetForProject_defaultAppRoot() throws IOException { "/app/libs/libraryA.jar", "/app/libs/libraryB.jar", "/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/app/resources/resourceA", "/app/resources/resourceB", "/app/resources/world"), - configuration.getResourceLayerEntries()); + resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), - configuration.getClassLayerEntries()); + classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void testWebApp() throws URISyntaxException, IOException { + public void testWebApp() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); setUpWarProject(webAppDirectory); - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")); - ImmutableList expectedDependenciesFiles = + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + + assertSourcePathsUnordered( ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")); - ImmutableList expectedSnapshotDependenciesFiles = + webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")), + dependenciesLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( - webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = + webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")), + snapshotsLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/META-INF"), webAppDirectory.resolve("jib-exploded-war/META-INF/context.xml"), @@ -513,36 +571,31 @@ public void testWebApp() throws URISyntaxException, IOException { webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/test.properties"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")); - ImmutableList expectedClassesFiles = + webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")), + resourcesLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/HelloWorld.class"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), - webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")); - ImmutableList expectedExtraFiles = + webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")), + classesLayerConfigurations.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), extraFilesDirectory.resolve("a/b"), extraFilesDirectory.resolve("a/b/bar"), extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedDependenciesFiles, configuration.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); - assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); - assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); + extraFilesDirectory.resolve("foo")), + extraFilesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/META-INF", @@ -555,99 +608,122 @@ public void testWebApp() throws URISyntaxException, IOException { "/my/app/WEB-INF/classes/package/test.properties", "/my/app/WEB-INF/lib", "/my/app/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); + resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/WEB-INF/classes/HelloWorld.class", "/my/app/WEB-INF/classes/empty_dir", "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); + classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void testWebApp_defaultWebAppRoot() throws URISyntaxException, IOException { + public void testWebApp_defaultWebAppRoot() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); - JavaLayerConfigurations configuration = - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); + BuildConfiguration configuration = + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + List resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + List classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + List dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + List snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + List extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); + Collections.singletonList("/jetty/webapps/root/WEB-INF/lib/dependency-1.0.0.jar"), + dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + Collections.singletonList("/jetty/webapps/root/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), + snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( - "/jetty/webapps/ROOT/META-INF", - "/jetty/webapps/ROOT/META-INF/context.xml", - "/jetty/webapps/ROOT/Test.jsp", - "/jetty/webapps/ROOT/WEB-INF", - "/jetty/webapps/ROOT/WEB-INF/classes", - "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", - "/jetty/webapps/ROOT/WEB-INF/classes/package", - "/jetty/webapps/ROOT/WEB-INF/classes/package/test.properties", - "/jetty/webapps/ROOT/WEB-INF/lib", - "/jetty/webapps/ROOT/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); + "/jetty/webapps/root/META-INF", + "/jetty/webapps/root/META-INF/context.xml", + "/jetty/webapps/root/Test.jsp", + "/jetty/webapps/root/WEB-INF", + "/jetty/webapps/root/WEB-INF/classes", + "/jetty/webapps/root/WEB-INF/classes/empty_dir", + "/jetty/webapps/root/WEB-INF/classes/package", + "/jetty/webapps/root/WEB-INF/classes/package/test.properties", + "/jetty/webapps/root/WEB-INF/lib", + "/jetty/webapps/root/WEB-INF/web.xml"), + resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( - "/jetty/webapps/ROOT/WEB-INF/classes/HelloWorld.class", - "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", - "/jetty/webapps/ROOT/WEB-INF/classes/package", - "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); + "/jetty/webapps/root/WEB-INF/classes/HelloWorld.class", + "/jetty/webapps/root/WEB-INF/classes/empty_dir", + "/jetty/webapps/root/WEB-INF/classes/package", + "/jetty/webapps/root/WEB-INF/classes/package/Other.class"), + classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() + throws IOException, InvalidImageReferenceException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); setUpWarProject(temporaryFolder.getRoot().toPath()); - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) + .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass } @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() + throws IOException, InvalidImageReferenceException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); setUpWarProject(temporaryFolder.getRoot().toPath()); - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) + .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass } @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfDoesNotExist() + throws IOException, InvalidImageReferenceException { temporaryFolder.newFolder("jib-exploded-war"); setUpWarProject(temporaryFolder.getRoot().toPath()); - GradleLayerConfigurations.getForProject( - mockWebAppProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)); // should pass + new GradleProjectProperties( + mockProject, + mockLogger, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) + .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass } private void setUpWarProject(Path webAppDirectory) { From 6acf1cf2b5eebfa172244dec638e6233db19ab62 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 20 Mar 2019 17:53:07 -0400 Subject: [PATCH 07/20] Gradle tests pass --- .../jib/gradle/GradleProjectProperties.java | 4 +- .../gradle/GradleProjectPropertiesTest.java | 201 ++++++++---------- .../common/JavaContainerBuilderHelper.java | 19 +- 3 files changed, 101 insertions(+), 123 deletions(-) diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index cfd07d2fc4..a8f090f26f 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -205,7 +205,9 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage // Adds class files for (File classesOutputDirectory : classesOutputDirectories) { - javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); + if (classesOutputDirectory.exists()) { + javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); + } } if (classesOutputDirectories.filter(File::exists).isEmpty()) { logger.warn("No classes files were found - did you compile your project?"); diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index f2032b6c72..2a742c081a 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -107,6 +107,29 @@ public TaskDependency getBuildDependencies() { } } + /** Helper for reading back layers in a {@code BuildConfiguration}. */ + private static class ContainerBuilderLayers { + + private final List resourcesLayerConfigurations; + private final List classesLayerConfigurations; + private final List dependenciesLayerConfigurations; + private final List snapshotsLayerConfigurations; + private final List extraFilesLayerConfigurations; + + private ContainerBuilderLayers(BuildConfiguration configuration) { + resourcesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + classesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + dependenciesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + snapshotsLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + extraFilesLayerConfigurations = + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + } + } + private static void assertLayerEntriesUnordered( List expectedPaths, List entries, Function fieldSelector) { List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); @@ -141,14 +164,12 @@ private static List getLayerConfigurationByName( @Mock private Jar mockJar2; @Mock private Project mockProject; @Mock private Convention mockConvention; - @Mock private WarPluginConvention mockWarPluginConvection; + @Mock private WarPluginConvention mockWarPluginConvention; @Mock private TaskContainer mockTaskContainer; @Mock private Logger mockLogger; @Mock private Gradle mockGradle; @Mock private StartParameter mockStartParameter; @Mock private JavaPluginConvention mockJavaPluginConvention; - @Mock private Project mockWebAppProject; - @Mock private WarPluginConvention mockWarPluginConvention; @Mock private SourceSetContainer mockSourceSetContainer; @Mock private SourceSet mockMainSourceSet; @Mock private SourceSetOutput mockMainSourceSetOutput; @@ -167,13 +188,8 @@ public void setup() throws URISyntaxException, IOException { Mockito.when(mockConvention.getPlugin(JavaPluginConvention.class)) .thenReturn(mockJavaPluginConvention); Mockito.when(mockJavaPluginConvention.getSourceSets()).thenReturn(mockSourceSetContainer); - Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)) - .thenReturn(mockWarPluginConvection); - Mockito.when(mockWarPluginConvection.getProject()).thenReturn(mockProject); Mockito.when(mockProject.getTasks()).thenReturn(mockTaskContainer); - Mockito.when(mockTaskContainer.findByName("war")).thenReturn(Mockito.mock(War.class)); Mockito.when(mockJar.getManifest()).thenReturn(manifest); - Mockito.when(mockProject.getGradle()).thenReturn(mockGradle); Mockito.when(mockGradle.getStartParameter()).thenReturn(mockStartParameter); Mockito.when(mockStartParameter.getConsoleOutput()).thenReturn(ConsoleOutput.Auto); @@ -255,17 +271,20 @@ public void testGetMainClassFromJar_multiple() { } @Test - public void testIsWarProject() { + public void testIsWarProject() throws URISyntaxException { + setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); Assert.assertTrue(gradleProjectProperties.isWarProject()); } @Test - public void testGetWar_warProject() { + public void testGetWar_warProject() throws URISyntaxException { + setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); Assert.assertNotNull(TaskCommon.getWarTask(mockProject)); } @Test - public void testGetWar_noWarPlugin() { + public void testGetWar_noWarPlugin() throws URISyntaxException { + setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)).thenReturn(null); Assert.assertNull(TaskCommon.getWarTask(mockProject)); @@ -273,8 +292,6 @@ public void testGetWar_noWarPlugin() { @Test public void testGetWar_noWarTask() { - Mockito.when(mockTaskContainer.findByName("war")).thenReturn(null); - Assert.assertNull(TaskCommon.getWarTask(mockProject)); } @@ -347,16 +364,7 @@ public void test_correctFiles() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependency-1.0.0.jar"), @@ -365,24 +373,23 @@ public void test_correctFiles() applicationDirectory.resolve("dependencies/libraryA.jar"), applicationDirectory.resolve("dependencies/libraryB.jar"), applicationDirectory.resolve("dependencies/library.jarC.jar")), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("resources/resourceA"), applicationDirectory.resolve("resources/resourceB"), applicationDirectory.resolve("resources/world")), - resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("classes/HelloWorld.class"), applicationDirectory.resolve("classes/some.class")), - classesLayerConfigurations.get(0).getLayerEntries()); - assertSourcePathsUnordered( - ImmutableList.of(), extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerConfigurations.get(0).getLayerEntries()); + Assert.assertEquals(0, layers.extraFilesLayerConfigurations.size()); } @Test @@ -437,16 +444,7 @@ public void testGetForProject_nonDefaultAppRoot() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Arrays.asList( "/my/app/libs/dependency-1.0.0-770.jar", @@ -455,22 +453,22 @@ public void testGetForProject_nonDefaultAppRoot() "/my/app/libs/libraryA.jar", "/my/app/libs/libraryB.jar", "/my/app/libs/library.jarC.jar"), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/resources/resourceA", "/my/app/resources/resourceB", "/my/app/resources/world"), - resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), - classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test @@ -488,16 +486,7 @@ public void testGetForProject_defaultAppRoot() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Arrays.asList( "/app/libs/dependency-1.0.0-770.jar", @@ -506,20 +495,20 @@ public void testGetForProject_defaultAppRoot() "/app/libs/libraryA.jar", "/app/libs/libraryB.jar", "/app/libs/library.jarC.jar"), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/app/resources/resourceA", "/app/resources/resourceB", "/app/resources/world"), - resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), - classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test @@ -541,25 +530,15 @@ public void testWebApp() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); - + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/META-INF"), @@ -572,14 +551,14 @@ public void testWebApp() webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/test.properties"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")), - resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/HelloWorld.class"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")), - classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerConfigurations.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), @@ -588,14 +567,14 @@ public void testWebApp() extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), extraFilesDirectory.resolve("foo")), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/META-INF", @@ -608,17 +587,17 @@ public void testWebApp() "/my/app/WEB-INF/classes/package/test.properties", "/my/app/WEB-INF/lib", "/my/app/WEB-INF/web.xml"), - resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/WEB-INF/classes/HelloWorld.class", "/my/app/WEB-INF/classes/empty_dir", "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), - classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test @@ -639,46 +618,36 @@ public void testWebApp_defaultWebAppRoot() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); - + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/root/WEB-INF/lib/dependency-1.0.0.jar"), - dependenciesLayerConfigurations.get(0).getLayerEntries()); + Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), + layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( - Collections.singletonList("/jetty/webapps/root/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - snapshotsLayerConfigurations.get(0).getLayerEntries()); + Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), + layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( - "/jetty/webapps/root/META-INF", - "/jetty/webapps/root/META-INF/context.xml", - "/jetty/webapps/root/Test.jsp", - "/jetty/webapps/root/WEB-INF", - "/jetty/webapps/root/WEB-INF/classes", - "/jetty/webapps/root/WEB-INF/classes/empty_dir", - "/jetty/webapps/root/WEB-INF/classes/package", - "/jetty/webapps/root/WEB-INF/classes/package/test.properties", - "/jetty/webapps/root/WEB-INF/lib", - "/jetty/webapps/root/WEB-INF/web.xml"), - resourcesLayerConfigurations.get(0).getLayerEntries()); + "/jetty/webapps/ROOT/META-INF", + "/jetty/webapps/ROOT/META-INF/context.xml", + "/jetty/webapps/ROOT/Test.jsp", + "/jetty/webapps/ROOT/WEB-INF", + "/jetty/webapps/ROOT/WEB-INF/classes", + "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", + "/jetty/webapps/ROOT/WEB-INF/classes/package", + "/jetty/webapps/ROOT/WEB-INF/classes/package/test.properties", + "/jetty/webapps/ROOT/WEB-INF/lib", + "/jetty/webapps/ROOT/WEB-INF/web.xml"), + layers.resourcesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( - "/jetty/webapps/root/WEB-INF/classes/HelloWorld.class", - "/jetty/webapps/root/WEB-INF/classes/empty_dir", - "/jetty/webapps/root/WEB-INF/classes/package", - "/jetty/webapps/root/WEB-INF/classes/package/Other.class"), - classesLayerConfigurations.get(0).getLayerEntries()); + "/jetty/webapps/ROOT/WEB-INF/classes/HelloWorld.class", + "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", + "/jetty/webapps/ROOT/WEB-INF/classes/package", + "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), + layers.classesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); } @Test @@ -727,12 +696,12 @@ public void testGetForWarProject_noErrorIfWebInfDoesNotExist() } private void setUpWarProject(Path webAppDirectory) { - Mockito.when(mockWebAppProject.getBuildDir()).thenReturn(webAppDirectory.toFile()); - Mockito.when(mockWebAppProject.getConvention()).thenReturn(mockConvention); + Mockito.when(mockProject.getBuildDir()).thenReturn(webAppDirectory.toFile()); + Mockito.when(mockProject.getConvention()).thenReturn(mockConvention); Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)) .thenReturn(mockWarPluginConvention); - Mockito.when(mockWarPluginConvention.getProject()).thenReturn(mockWebAppProject); - Mockito.when(mockWebAppProject.getTasks()).thenReturn(taskContainer); + Mockito.when(mockWarPluginConvention.getProject()).thenReturn(mockProject); + Mockito.when(mockProject.getTasks()).thenReturn(taskContainer); Mockito.when(taskContainer.findByName("war")).thenReturn(war); } } diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index dc6e186312..b5313ef732 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -85,16 +85,23 @@ public static JibContainerBuilder fromExplodedWar( path -> path.startsWith(webInfClasses) && path.getFileName().toString().endsWith(".class"); Predicate isResource = isDependency.or(isClassFile).negate(); - JibContainerBuilder jibContainerBuilder = + JavaContainerBuilder javaContainerBuilder = JavaContainerBuilder.from(baseImage) .setAppRoot(appRoot) .setResourcesDestination(RelativeUnixPath.get("")) .setClassesDestination(RelativeUnixPath.get("WEB-INF/classes")) - .setDependenciesDestination(RelativeUnixPath.get("WEB-INF/lib")) - .addResources(explodedWar, isResource) - .addClasses(webInfClasses, isClassFile) - .addDependencies(webInfLib, isDependency) - .toContainerBuilder(); + .setDependenciesDestination(RelativeUnixPath.get("WEB-INF/lib")); + + if (Files.exists(explodedWar)) { + javaContainerBuilder.addResources(explodedWar, isResource); + } + if (Files.exists(webInfClasses)) { + javaContainerBuilder.addClasses(webInfClasses, isClassFile); + } + if (Files.exists(webInfLib)) { + javaContainerBuilder.addDependencies(webInfLib, isDependency); + } + JibContainerBuilder jibContainerBuilder = javaContainerBuilder.toContainerBuilder(); // Adds all the extra files. if (Files.exists(extraFilesDirectory)) { From 8cb7202032637ddf9a71c46d77e3e7525323fcef Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 11:14:44 -0400 Subject: [PATCH 08/20] Tests pass --- .../gradle/GradleProjectPropertiesTest.java | 93 +++--- .../jib/maven/MavenProjectPropertiesTest.java | 292 ++++++++++++------ 2 files changed, 244 insertions(+), 141 deletions(-) diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index 2a742c081a..f159506543 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -110,22 +110,21 @@ public TaskDependency getBuildDependencies() { /** Helper for reading back layers in a {@code BuildConfiguration}. */ private static class ContainerBuilderLayers { - private final List resourcesLayerConfigurations; - private final List classesLayerConfigurations; - private final List dependenciesLayerConfigurations; - private final List snapshotsLayerConfigurations; - private final List extraFilesLayerConfigurations; + private final List resourcesLayerEntries; + private final List classesLayerEntries; + private final List dependenciesLayerEntries; + private final List snapshotsLayerEntries; + private final List extraFilesLayerEntries; private ContainerBuilderLayers(BuildConfiguration configuration) { - resourcesLayerConfigurations = + resourcesLayerEntries = getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); - dependenciesLayerConfigurations = + classesLayerEntries = getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + dependenciesLayerEntries = getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); - snapshotsLayerConfigurations = + snapshotsLayerEntries = getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - extraFilesLayerConfigurations = + extraFilesLayerEntries = getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); } } @@ -365,6 +364,10 @@ public void test_correctFiles() MoreExecutors.newDirectExecutorService()); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + assertSourcePathsUnordered( + ImmutableList.of( + applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependency-1.0.0.jar"), @@ -373,23 +376,19 @@ public void test_correctFiles() applicationDirectory.resolve("dependencies/libraryA.jar"), applicationDirectory.resolve("dependencies/libraryB.jar"), applicationDirectory.resolve("dependencies/library.jarC.jar")), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); - assertSourcePathsUnordered( - ImmutableList.of( - applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("resources/resourceA"), applicationDirectory.resolve("resources/resourceB"), applicationDirectory.resolve("resources/world")), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("classes/HelloWorld.class"), applicationDirectory.resolve("classes/some.class")), - layers.classesLayerConfigurations.get(0).getLayerEntries()); - Assert.assertEquals(0, layers.extraFilesLayerConfigurations.size()); + layers.classesLayerEntries.get(0).getLayerEntries()); + Assert.assertEquals(0, layers.extraFilesLayerEntries.size()); } @Test @@ -416,8 +415,6 @@ public void test_extraFiles() Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), @@ -426,7 +423,9 @@ public void test_extraFiles() extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), extraFilesDirectory.resolve("foo")), - extraFilesLayerConfigurations.get(0).getLayerEntries()); + getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()) + .get(0) + .getLayerEntries()); } @Test @@ -453,22 +452,22 @@ public void testGetForProject_nonDefaultAppRoot() "/my/app/libs/libraryA.jar", "/my/app/libs/libraryB.jar", "/my/app/libs/library.jarC.jar"), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/resources/resourceA", "/my/app/resources/resourceB", "/my/app/resources/world"), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), - layers.classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -495,20 +494,20 @@ public void testGetForProject_defaultAppRoot() "/app/libs/libraryA.jar", "/app/libs/libraryB.jar", "/app/libs/library.jarC.jar"), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/app/resources/resourceA", "/app/resources/resourceB", "/app/resources/world"), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), - layers.classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -534,11 +533,11 @@ public void testWebApp() assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependency-1.0.0.jar")), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/META-INF"), @@ -551,14 +550,14 @@ public void testWebApp() webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/test.properties"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/lib"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/web.xml")), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/HelloWorld.class"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/empty_dir"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")), - layers.classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), @@ -567,14 +566,14 @@ public void testWebApp() extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), extraFilesDirectory.resolve("foo")), - layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/META-INF", @@ -587,17 +586,17 @@ public void testWebApp() "/my/app/WEB-INF/classes/package/test.properties", "/my/app/WEB-INF/lib", "/my/app/WEB-INF/web.xml"), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/WEB-INF/classes/HelloWorld.class", "/my/app/WEB-INF/classes/empty_dir", "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), - layers.classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -621,10 +620,10 @@ public void testWebApp_defaultWebAppRoot() ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), - layers.dependenciesLayerConfigurations.get(0).getLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - layers.snapshotsLayerConfigurations.get(0).getLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/jetty/webapps/ROOT/META-INF", @@ -637,17 +636,17 @@ public void testWebApp_defaultWebAppRoot() "/jetty/webapps/ROOT/WEB-INF/classes/package/test.properties", "/jetty/webapps/ROOT/WEB-INF/lib", "/jetty/webapps/ROOT/WEB-INF/web.xml"), - layers.resourcesLayerConfigurations.get(0).getLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/jetty/webapps/ROOT/WEB-INF/classes/HelloWorld.class", "/jetty/webapps/ROOT/WEB-INF/classes/empty_dir", "/jetty/webapps/ROOT/WEB-INF/classes/package", "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), - layers.classesLayerConfigurations.get(0).getLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerConfigurations.get(0).getLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 4d7ee62929..740da18670 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -16,13 +16,20 @@ package com.google.cloud.tools.jib.maven; +import com.google.cloud.tools.jib.api.Containerizer; +import com.google.cloud.tools.jib.api.RegistryImage; +import com.google.cloud.tools.jib.configuration.BuildConfiguration; +import com.google.cloud.tools.jib.configuration.CacheDirectoryCreationException; +import com.google.cloud.tools.jib.configuration.LayerConfiguration; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; +import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; +import com.google.cloud.tools.jib.image.InvalidImageReferenceException; import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; import com.google.common.io.Resources; +import com.google.common.util.concurrent.MoreExecutors; import java.io.IOException; import java.net.URISyntaxException; import java.nio.file.Files; @@ -57,6 +64,27 @@ @RunWith(MockitoJUnitRunner.class) public class MavenProjectPropertiesTest { + /** Helper for reading back layers in a {@code BuildConfiguration}. */ + private static class ContainerBuilderLayers { + + private final List resourcesLayerEntries; + private final List classesLayerEntries; + private final List dependenciesLayerEntries; + private final List snapshotsLayerEntries; + private final List extraFilesLayerEntries; + + private ContainerBuilderLayers(BuildConfiguration configuration) { + resourcesLayerEntries = getLayerEntriesByName(configuration, LayerType.RESOURCES.getName()); + classesLayerEntries = getLayerEntriesByName(configuration, LayerType.CLASSES.getName()); + dependenciesLayerEntries = + getLayerEntriesByName(configuration, LayerType.DEPENDENCIES.getName()); + snapshotsLayerEntries = + getLayerEntriesByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + extraFilesLayerEntries = + getLayerEntriesByName(configuration, LayerType.EXTRA_FILES.getName()); + } + } + private static void assertLayerEntriesUnordered( List expectedPaths, List entries, Function fieldSelector) { List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); @@ -75,7 +103,8 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } - private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuration) { + private static void assertNonDefaultAppRoot(BuildConfiguration configuration) { + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Arrays.asList( "/my/app/libs/dependency-1.0.0-770.jar", @@ -84,10 +113,10 @@ private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuratio "/my/app/libs/libraryA.jar", "/my/app/libs/libraryB.jar", "/my/app/libs/library.jarC.jar"), - configuration.getDependencyLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/libs/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/resources/directory", @@ -96,7 +125,7 @@ private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuratio "/my/app/resources/resourceA", "/my/app/resources/resourceB", "/my/app/resources/world"), - configuration.getResourceLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/classes/HelloWorld.class", @@ -104,10 +133,19 @@ private static void assertNonDefaultAppRoot(JavaLayerConfigurations configuratio "/my/app/classes/package", "/my/app/classes/package/some.class", "/my/app/classes/some.class"), - configuration.getClassLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); + } + + private static List getLayerEntriesByName( + BuildConfiguration buildConfiguration, String name) { + return buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals(name)) + .collect(Collectors.toList()); } @Rule public final TestRepository testRepository = new TestRepository(); @@ -331,102 +369,137 @@ public void isProgressFooterEnabled() { } @Test - public void test_correctFiles() throws URISyntaxException, IOException { + public void test_correctFiles() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { Path dependenciesPath = Paths.get(Resources.getResource("maven/application/dependencies").toURI()); - ImmutableList expectedDependenciesFiles = + Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); + BuildConfiguration configuration = + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + Paths.get("nonexistent/path"), + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + assertSourcePathsUnordered( ImmutableList.of( testRepository.artifactPathOnDisk("com.test", "dependency", "1.0.0"), dependenciesPath.resolve("more").resolve("dependency-1.0.0.jar"), dependenciesPath.resolve("another").resolve("one").resolve("dependency-1.0.0.jar"), dependenciesPath.resolve("libraryA.jar"), dependenciesPath.resolve("libraryB.jar"), - dependenciesPath.resolve("library.jarC.jar")); - ImmutableList expectedSnapshotDependenciesFiles = + dependenciesPath.resolve("library.jarC.jar")), + layers.dependenciesLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( - testRepository.artifactPathOnDisk("com.test", "dependencyX", "1.0.0-SNAPSHOT")); - Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); - ImmutableList expectedResourcesFiles = + testRepository.artifactPathOnDisk("com.test", "dependencyX", "1.0.0-SNAPSHOT")), + layers.snapshotsLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("output/directory"), applicationDirectory.resolve("output/directory/somefile"), applicationDirectory.resolve("output/package"), applicationDirectory.resolve("output/resourceA"), applicationDirectory.resolve("output/resourceB"), - applicationDirectory.resolve("output/world")); - ImmutableList expectedClassesFiles = + applicationDirectory.resolve("output/world")), + layers.resourcesLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("output/HelloWorld.class"), applicationDirectory.resolve("output/directory"), applicationDirectory.resolve("output/package"), applicationDirectory.resolve("output/package/some.class"), - applicationDirectory.resolve("output/some.class")); - - JavaLayerConfigurations javaLayerConfigurations = - MavenLayerConfigurations.getForProject( - mockMavenProject, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")); - assertSourcePathsUnordered( - expectedDependenciesFiles, javaLayerConfigurations.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, - javaLayerConfigurations.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedResourcesFiles, javaLayerConfigurations.getResourceLayerEntries()); - assertSourcePathsUnordered( - expectedClassesFiles, javaLayerConfigurations.getClassLayerEntries()); + applicationDirectory.resolve("output/some.class")), + layers.classesLayerEntries.get(0).getLayerEntries()); } @Test - public void test_extraFiles() throws IOException { - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); - JavaLayerConfigurations javaLayerConfigurations = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + public void test_extraFiles() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); - ImmutableList expectedExtraFiles = + assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), extraFilesDirectory.resolve("a/b"), extraFilesDirectory.resolve("a/b/bar"), extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedExtraFiles, javaLayerConfigurations.getExtraFilesLayerEntries()); + extraFilesDirectory.resolve("foo")), + getLayerEntriesByName(configuration, LayerType.EXTRA_FILES.getName()) + .get(0) + .getLayerEntries()); } @Test - public void testGetForProject_nonDefaultAppRoot() throws IOException { - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + public void testGetForProject_nonDefaultAppRoot() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); assertNonDefaultAppRoot(configuration); } @Test - public void testGetForWarProject_nonDefaultAppRoot() throws URISyntaxException, IOException { + public void testGetForWarProject_nonDefaultAppRoot() + throws URISyntaxException, IOException, InvalidImageReferenceException, + CacheDirectoryCreationException { Path outputPath = Paths.get(Resources.getResource("maven/webapp").toURI()); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); Mockito.when(mockBuild.getDirectory()).thenReturn(outputPath.toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); - - ImmutableList expectedDependenciesFiles = - ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")); - ImmutableList expectedSnapshotDependenciesFiles = + BuildConfiguration configuration = + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); + + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + assertSourcePathsUnordered( + ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")), + layers.dependenciesLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( - outputPath.resolve("final-name/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")); - ImmutableList expectedResourcesFiles = + outputPath.resolve("final-name/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar")), + layers.snapshotsLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( outputPath.resolve("final-name/META-INF"), outputPath.resolve("final-name/META-INF/context.xml"), @@ -437,36 +510,31 @@ public void testGetForWarProject_nonDefaultAppRoot() throws URISyntaxException, outputPath.resolve("final-name/WEB-INF/classes/package"), outputPath.resolve("final-name/WEB-INF/classes/package/test.properties"), outputPath.resolve("final-name/WEB-INF/lib"), - outputPath.resolve("final-name/WEB-INF/web.xml")); - ImmutableList expectedClassesFiles = + outputPath.resolve("final-name/WEB-INF/web.xml")), + layers.resourcesLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( outputPath.resolve("final-name/WEB-INF/classes/HelloWorld.class"), outputPath.resolve("final-name/WEB-INF/classes/empty_dir"), outputPath.resolve("final-name/WEB-INF/classes/package"), - outputPath.resolve("final-name/WEB-INF/classes/package/Other.class")); - ImmutableList expectedExtraFiles = + outputPath.resolve("final-name/WEB-INF/classes/package/Other.class")), + layers.classesLayerEntries.get(0).getLayerEntries()); + assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), extraFilesDirectory.resolve("a/b"), extraFilesDirectory.resolve("a/b/bar"), extraFilesDirectory.resolve("c"), extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")); - - assertSourcePathsUnordered( - expectedDependenciesFiles, configuration.getDependencyLayerEntries()); - assertSourcePathsUnordered( - expectedSnapshotDependenciesFiles, configuration.getSnapshotDependencyLayerEntries()); - assertSourcePathsUnordered(expectedResourcesFiles, configuration.getResourceLayerEntries()); - assertSourcePathsUnordered(expectedClassesFiles, configuration.getClassLayerEntries()); - assertSourcePathsUnordered(expectedExtraFiles, configuration.getExtraFilesLayerEntries()); + extraFilesDirectory.resolve("foo")), + layers.extraFilesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), - configuration.getDependencyLayerEntries()); + layers.dependenciesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependencyX-1.0.0-SNAPSHOT.jar"), - configuration.getSnapshotDependencyLayerEntries()); + layers.snapshotsLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/META-INF", @@ -479,69 +547,105 @@ public void testGetForWarProject_nonDefaultAppRoot() throws URISyntaxException, "/my/app/WEB-INF/classes/package/test.properties", "/my/app/WEB-INF/lib", "/my/app/WEB-INF/web.xml"), - configuration.getResourceLayerEntries()); + layers.resourcesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList( "/my/app/WEB-INF/classes/HelloWorld.class", "/my/app/WEB-INF/classes/empty_dir", "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), - configuration.getClassLayerEntries()); + layers.classesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - configuration.getExtraFilesLayerEntries()); + layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test - public void testGetForJarProject_nonDefaultAppRoot() throws IOException { + public void testGetForJarProject_nonDefaultAppRoot() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { // Test when the default packaging is set Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - JavaLayerConfigurations configuration = - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); + BuildConfiguration configuration = + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); assertNonDefaultAppRoot(configuration); } @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfDoesNotExist() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); Mockito.when(mockBuild.getDirectory()) .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); // should pass } @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "classes"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); Mockito.when(mockBuild.getDirectory()) .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); // should pass } @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() throws IOException { + public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "lib"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); Mockito.when(mockBuild.getDirectory()) .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/my/app"); - MavenLayerConfigurations.getForProject( - mockMavenProject, extraFilesDirectory, Collections.emptyMap(), appRoot); // should pass + new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + AbsoluteUnixPath.get("/my/app")) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), + MoreExecutors.newDirectExecutorService()); // should pass } @Test From 30fec16bfd27c6d28bc4b7c291cea044896807b1 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 11:30:51 -0400 Subject: [PATCH 09/20] Test cleanup --- .../gradle/GradleProjectPropertiesTest.java | 118 ++++------------- .../jib/maven/MavenProjectPropertiesTest.java | 121 ++++-------------- 2 files changed, 52 insertions(+), 187 deletions(-) diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index f159506543..cc8a5fbd1d 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -350,20 +350,11 @@ public void testGetMajorJavaVersion_jvm11() { public void test_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(Paths.get("nonexistent/path"), "/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + + Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), @@ -403,18 +394,7 @@ public void test_noClassesFiles() throws InvalidImageReferenceException { @Test public void test_extraFiles() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/app"); assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), @@ -431,19 +411,9 @@ public void test_extraFiles() @Test public void testGetForProject_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + assertExtractionPathsUnordered( Arrays.asList( "/my/app/libs/dependency-1.0.0-770.jar", @@ -474,17 +444,7 @@ public void testGetForProject_nonDefaultAppRoot() public void testGetForProject_defaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_APP_ROOT)) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_APP_ROOT); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Arrays.asList( @@ -517,18 +477,7 @@ public void testWebApp() Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); setUpWarProject(webAppDirectory); - BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of( @@ -606,17 +555,7 @@ public void testWebApp_defaultWebAppRoot() setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); BuildConfiguration configuration = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), @@ -651,47 +590,42 @@ public void testWebApp_defaultWebAppRoot() @Test public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() - throws IOException, InvalidImageReferenceException { + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); setUpWarProject(temporaryFolder.getRoot().toPath()); - - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) - .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass + setupBuildConfiguration( + extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass } @Test public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() - throws IOException, InvalidImageReferenceException { + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); setUpWarProject(temporaryFolder.getRoot().toPath()); - - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) - .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass + setupBuildConfiguration( + extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass } @Test public void testGetForWarProject_noErrorIfWebInfDoesNotExist() - throws IOException, InvalidImageReferenceException { + throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war"); setUpWarProject(temporaryFolder.getRoot().toPath()); + setupBuildConfiguration( + extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass + } - new GradleProjectProperties( + private BuildConfiguration setupBuildConfiguration(Path extraFilesDirectory, String appRoot) + throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { + return new GradleProjectProperties( mockProject, mockLogger, extraFilesDirectory, Collections.emptyMap(), - AbsoluteUnixPath.get(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT)) - .getContainerBuilderWithLayers(RegistryImage.named("base")); // should pass + AbsoluteUnixPath.get(appRoot)) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); } private void setUpWarProject(Path webAppDirectory) { diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 740da18670..226a10495f 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -372,23 +372,13 @@ public void isProgressFooterEnabled() { public void test_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { + BuildConfiguration configuration = + setupBuildConfiguration(Paths.get("nonexistent"), AbsoluteUnixPath.get("/app")); + ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); + Path dependenciesPath = Paths.get(Resources.getResource("maven/application/dependencies").toURI()); Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); - BuildConfiguration configuration = - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - Paths.get("nonexistent/path"), - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - - ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of( testRepository.artifactPathOnDisk("com.test", "dependency", "1.0.0"), @@ -425,18 +415,7 @@ public void test_correctFiles() public void test_extraFiles() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/app")); assertSourcePathsUnordered( ImmutableList.of( extraFilesDirectory.resolve("a"), @@ -454,18 +433,7 @@ public void test_extraFiles() public void testGetForProject_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); } @@ -479,18 +447,7 @@ public void testGetForWarProject_nonDefaultAppRoot() Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); BuildConfiguration configuration = - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")), @@ -567,18 +524,7 @@ public void testGetForJarProject_nonDefaultAppRoot() Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); BuildConfiguration configuration = - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); - + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); } @@ -591,17 +537,7 @@ public void testGetForWarProject_noErrorIfWebInfDoesNotExist() .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); // should pass + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -613,17 +549,7 @@ public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); // should pass + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -635,17 +561,7 @@ public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get("/my/app")) - .getContainerBuilderWithLayers(RegistryImage.named("base")) - .toBuildConfiguration( - Containerizer.to(RegistryImage.named("to")), - MoreExecutors.newDirectExecutorService()); // should pass + setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -675,4 +591,19 @@ public void testIsWarProject_GwtLibPackagingIsNotWar() { Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); } + + private BuildConfiguration setupBuildConfiguration( + Path extraFilesDirectory, AbsoluteUnixPath appRoot) + throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { + return new MavenProjectProperties( + mockMavenProject, + mockMavenSession, + mockLog, + extraFilesDirectory, + Collections.emptyMap(), + appRoot) + .getContainerBuilderWithLayers(RegistryImage.named("base")) + .toBuildConfiguration( + Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); + } } From 5c0b824d12984cefefa3f2dd90b567a9869f95e5 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 12:47:56 -0400 Subject: [PATCH 10/20] Cleanup --- .../jib/gradle/GradleProjectProperties.java | 2 +- .../gradle/GradleProjectPropertiesTest.java | 39 ++++++++++--------- .../jib/maven/MavenProjectPropertiesTest.java | 34 ++++++++-------- .../common/JavaContainerBuilderHelper.java | 7 ++-- 4 files changed, 41 insertions(+), 41 deletions(-) diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index a8f090f26f..4484cc87a7 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -204,7 +204,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage } // Adds class files - for (File classesOutputDirectory : classesOutputDirectories) { + for (File classesOutputDirectory : classesOutputDirectories.filter(File::exists)) { if (classesOutputDirectory.exists()) { javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); } diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index cc8a5fbd1d..b04948530f 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -129,6 +129,15 @@ private ContainerBuilderLayers(BuildConfiguration configuration) { } } + private static List getLayerConfigurationByName( + BuildConfiguration buildConfiguration, String name) { + return buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals(name)) + .collect(Collectors.toList()); + } + private static void assertLayerEntriesUnordered( List expectedPaths, List entries, Function fieldSelector) { List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); @@ -147,15 +156,6 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } - private static List getLayerConfigurationByName( - BuildConfiguration buildConfiguration, String name) { - return buildConfiguration - .getLayerConfigurations() - .stream() - .filter(layer -> layer.getName().equals(name)) - .collect(Collectors.toList()); - } - @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @Mock private FileResolver mockFileResolver; @@ -347,7 +347,7 @@ public void testGetMajorJavaVersion_jvm11() { } @Test - public void test_correctFiles() + public void testGetContainerBuilderWithLayers_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = @@ -383,7 +383,8 @@ public void test_correctFiles() } @Test - public void test_noClassesFiles() throws InvalidImageReferenceException { + public void testGetContainerBuilderWithLayers_noClassesFiles() + throws InvalidImageReferenceException { Path nonexistentFile = Paths.get("/nonexistent/file"); Mockito.when(mockMainSourceSetOutput.getClassesDirs()) .thenReturn(new TestFileCollection(ImmutableSet.of(nonexistentFile))); @@ -392,7 +393,7 @@ public void test_noClassesFiles() throws InvalidImageReferenceException { } @Test - public void test_extraFiles() + public void testGetContainerBuilderWithLayers_extraFiles() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/app"); assertSourcePathsUnordered( @@ -409,7 +410,7 @@ public void test_extraFiles() } @Test - public void testGetForProject_nonDefaultAppRoot() + public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); @@ -441,7 +442,7 @@ public void testGetForProject_nonDefaultAppRoot() } @Test - public void testGetForProject_defaultAppRoot() + public void testGetContainerBuilderWithLayers_defaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_APP_ROOT); @@ -471,7 +472,7 @@ public void testGetForProject_defaultAppRoot() } @Test - public void testWebApp() + public void testGetContainerBuilderWithLayers_war() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); @@ -549,7 +550,7 @@ public void testWebApp() } @Test - public void testWebApp_defaultWebAppRoot() + public void testGetContainerBuilderWithLayers_defaultWebAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); @@ -589,7 +590,7 @@ public void testWebApp_defaultWebAppRoot() } @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); setUpWarProject(temporaryFolder.getRoot().toPath()); @@ -598,7 +599,7 @@ public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() } @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); setUpWarProject(temporaryFolder.getRoot().toPath()); @@ -607,7 +608,7 @@ public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() } @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war"); setUpWarProject(temporaryFolder.getRoot().toPath()); diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 226a10495f..566ca92f5b 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -85,6 +85,15 @@ private ContainerBuilderLayers(BuildConfiguration configuration) { } } + private static List getLayerEntriesByName( + BuildConfiguration buildConfiguration, String name) { + return buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals(name)) + .collect(Collectors.toList()); + } + private static void assertLayerEntriesUnordered( List expectedPaths, List entries, Function fieldSelector) { List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); @@ -139,15 +148,6 @@ private static void assertNonDefaultAppRoot(BuildConfiguration configuration) { layers.extraFilesLayerEntries.get(0).getLayerEntries()); } - private static List getLayerEntriesByName( - BuildConfiguration buildConfiguration, String name) { - return buildConfiguration - .getLayerConfigurations() - .stream() - .filter(layer -> layer.getName().equals(name)) - .collect(Collectors.toList()); - } - @Rule public final TestRepository testRepository = new TestRepository(); @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @@ -369,7 +369,7 @@ public void isProgressFooterEnabled() { } @Test - public void test_correctFiles() + public void testGetContainerBuilderWithLayers_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = @@ -412,7 +412,7 @@ public void test_correctFiles() } @Test - public void test_extraFiles() + public void testGetContainerBuilderWithLayers_extraFiles() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/app")); @@ -430,7 +430,7 @@ public void test_extraFiles() } @Test - public void testGetForProject_nonDefaultAppRoot() + public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); @@ -438,7 +438,7 @@ public void testGetForProject_nonDefaultAppRoot() } @Test - public void testGetForWarProject_nonDefaultAppRoot() + public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { Path outputPath = Paths.get(Resources.getResource("maven/webapp").toURI()); @@ -518,7 +518,7 @@ public void testGetForWarProject_nonDefaultAppRoot() } @Test - public void testGetForJarProject_nonDefaultAppRoot() + public void testGetContainerBuilderWithLayers_jarNonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { // Test when the default packaging is set Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); @@ -529,7 +529,7 @@ public void testGetForJarProject_nonDefaultAppRoot() } @Test - public void testGetForWarProject_noErrorIfWebInfDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); @@ -541,7 +541,7 @@ public void testGetForWarProject_noErrorIfWebInfDoesNotExist() } @Test - public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "classes"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); @@ -553,7 +553,7 @@ public void testGetForWarProject_noErrorIfWebInfLibDoesNotExist() } @Test - public void testGetForWarProject_noErrorIfWebInfClassesDoesNotExist() + public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "lib"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index b5313ef732..ac690a2d76 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -24,7 +24,6 @@ import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.filesystem.DirectoryWalker; import com.google.cloud.tools.jib.filesystem.RelativeUnixPath; -import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations.LayerType; import java.io.IOException; import java.nio.file.Files; @@ -32,7 +31,7 @@ import java.util.Map; import java.util.function.Predicate; -/** Helper for constructing {@link JavaLayerConfigurations}. */ +/** Helper for constructing {@link JavaContainerBuilder}-based {@link JibContainerBuilder}s. */ public class JavaContainerBuilderHelper { /** @@ -61,14 +60,14 @@ public static LayerConfiguration extraDirectoryLayerConfiguration( } /** - * Constructs a new {@link JavaLayerConfigurations} for a WAR project. + * Constructs a new {@link JibContainerBuilder} for a WAR project. * * @param baseImage the base image of the container * @param explodedWar the exploded WAR directory * @param appRoot root directory in the image where the app will be placed * @param extraFilesDirectory path to the source directory for the extra files layer * @param extraDirectoryPermissions map from path on container to file permissions - * @return {@link JavaLayerConfigurations} for the layers for the exploded WAR + * @return {@link JibContainerBuilder} containing the layers for the exploded WAR * @throws IOException if adding layer contents fails */ public static JibContainerBuilder fromExplodedWar( From 95eee03a5c9de45e00f19da45d47b23279169bce Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 15:09:28 -0400 Subject: [PATCH 11/20] More cleanup --- .../gradle/GradleProjectPropertiesTest.java | 58 +++++++------------ .../jib/maven/MavenProjectPropertiesTest.java | 26 ++++----- 2 files changed, 33 insertions(+), 51 deletions(-) diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index b04948530f..580fca8667 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -156,6 +156,10 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } + private static Path getResource(String path) throws URISyntaxException { + return Paths.get(Resources.getResource(path).toURI()); + } + @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @Mock private FileResolver mockFileResolver; @@ -193,38 +197,21 @@ public void setup() throws URISyntaxException, IOException { Mockito.when(mockGradle.getStartParameter()).thenReturn(mockStartParameter); Mockito.when(mockStartParameter.getConsoleOutput()).thenReturn(ConsoleOutput.Auto); - Set classesFiles = - ImmutableSet.of(Paths.get(Resources.getResource("gradle/application/classes").toURI())); + Set classesFiles = ImmutableSet.of(getResource("gradle/application/classes")); FileCollection classesFileCollection = new TestFileCollection(classesFiles); - Path resourcesOutputDir = - Paths.get(Resources.getResource("gradle/application/resources").toURI()); + Path resourcesOutputDir = getResource("gradle/application/resources"); Set allFiles = new HashSet<>(classesFiles); allFiles.add(resourcesOutputDir); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/library.jarC.jar").toURI())); - allFiles.add( - Paths.get(Resources.getResource("gradle/application/dependencies/libraryB.jar").toURI())); - allFiles.add( - Paths.get(Resources.getResource("gradle/application/dependencies/libraryA.jar").toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/dependency-1.0.0.jar").toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/more/dependency-1.0.0.jar") - .toURI())); - allFiles.add( - Paths.get( - Resources.getResource( - "gradle/application/dependencies/another/one/dependency-1.0.0.jar") - .toURI())); - allFiles.add( - Paths.get( - Resources.getResource("gradle/application/dependencies/dependencyX-1.0.0-SNAPSHOT.jar") - .toURI())); + allFiles.add(getResource("gradle/application/dependencies/library.jarC.jar")); + allFiles.add(getResource("gradle/application/dependencies/libraryB.jar")); + allFiles.add(getResource("gradle/application/dependencies/libraryA.jar")); + allFiles.add(getResource("gradle/application/dependencies/dependency-1.0.0.jar")); + allFiles.add(getResource("gradle/application/dependencies/more/dependency-1.0.0.jar")); + allFiles.add(getResource("gradle/application/dependencies/another/one/dependency-1.0.0.jar")); + allFiles.add(getResource("gradle/application/dependencies/dependencyX-1.0.0-SNAPSHOT.jar")); FileCollection runtimeFileCollection = new TestFileCollection(allFiles); + Mockito.when(mockSourceSetContainer.getByName("main")).thenReturn(mockMainSourceSet); Mockito.when(mockMainSourceSet.getOutput()).thenReturn(mockMainSourceSetOutput); Mockito.when(mockMainSourceSetOutput.getClassesDirs()).thenReturn(classesFileCollection); @@ -233,11 +220,10 @@ public void setup() throws URISyntaxException, IOException { // We can't commit an empty directory in Git, so create (if not exist). Path emptyDirectory = - Paths.get(Resources.getResource("gradle/webapp").toURI()) - .resolve("jib-exploded-war/WEB-INF/classes/empty_dir"); + getResource("gradle/webapp").resolve("jib-exploded-war/WEB-INF/classes/empty_dir"); Files.createDirectories(emptyDirectory); - extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + extraFilesDirectory = getResource("core/layer"); gradleProjectProperties = new GradleProjectProperties( @@ -271,19 +257,19 @@ public void testGetMainClassFromJar_multiple() { @Test public void testIsWarProject() throws URISyntaxException { - setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); + setUpWarProject(getResource("gradle/webapp")); Assert.assertTrue(gradleProjectProperties.isWarProject()); } @Test public void testGetWar_warProject() throws URISyntaxException { - setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); + setUpWarProject(getResource("gradle/webapp")); Assert.assertNotNull(TaskCommon.getWarTask(mockProject)); } @Test public void testGetWar_noWarPlugin() throws URISyntaxException { - setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); + setUpWarProject(getResource("gradle/webapp")); Mockito.when(mockConvention.findPlugin(WarPluginConvention.class)).thenReturn(null); Assert.assertNull(TaskCommon.getWarTask(mockProject)); @@ -354,7 +340,7 @@ public void testGetContainerBuilderWithLayers_correctFiles() setupBuildConfiguration(Paths.get("nonexistent/path"), "/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); - Path applicationDirectory = Paths.get(Resources.getResource("gradle/application").toURI()); + Path applicationDirectory = getResource("gradle/application"); assertSourcePathsUnordered( ImmutableList.of( applicationDirectory.resolve("dependencies/dependencyX-1.0.0-SNAPSHOT.jar")), @@ -475,7 +461,7 @@ public void testGetContainerBuilderWithLayers_defaultAppRoot() public void testGetContainerBuilderWithLayers_war() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - Path webAppDirectory = Paths.get(Resources.getResource("gradle/webapp").toURI()); + Path webAppDirectory = getResource("gradle/webapp"); setUpWarProject(webAppDirectory); BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); @@ -553,7 +539,7 @@ public void testGetContainerBuilderWithLayers_war() public void testGetContainerBuilderWithLayers_defaultWebAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - setUpWarProject(Paths.get(Resources.getResource("gradle/webapp").toURI())); + setUpWarProject(getResource("gradle/webapp")); BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 566ca92f5b..568712cf3b 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -148,6 +148,10 @@ private static void assertNonDefaultAppRoot(BuildConfiguration configuration) { layers.extraFilesLayerEntries.get(0).getLayerEntries()); } + private static Path getResource(String path) throws URISyntaxException { + return Paths.get(Resources.getResource(path).toURI()); + } + @Rule public final TestRepository testRepository = new TestRepository(); @Rule public final TemporaryFolder temporaryFolder = new TemporaryFolder(); @@ -188,9 +192,8 @@ public void setup() throws IOException, URISyntaxException { manifest = new Xpp3Dom("manifest"); jarPluginMainClass = new Xpp3Dom("mainClass"); - Path outputPath = Paths.get(Resources.getResource("maven/application/output").toURI()); - Path dependenciesPath = - Paths.get(Resources.getResource("maven/application/dependencies").toURI()); + Path outputPath = getResource("maven/application/output"); + Path dependenciesPath = getResource("maven/application/dependencies"); Mockito.when(mockMavenProject.getBuild()).thenReturn(mockBuild); Mockito.when(mockBuild.getOutputDirectory()).thenReturn(outputPath.toString()); @@ -210,11 +213,10 @@ public void setup() throws IOException, URISyntaxException { Mockito.when(mockMavenProject.getArtifacts()).thenReturn(artifacts); Path emptyDirectory = - Paths.get(Resources.getResource("maven/webapp").toURI()) - .resolve("final-name/WEB-INF/classes/empty_dir"); + getResource("maven/webapp").resolve("final-name/WEB-INF/classes/empty_dir"); Files.createDirectories(emptyDirectory); - extraFilesDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + extraFilesDirectory = getResource("core/layer"); Mockito.when(mockMavenProject.getProperties()).thenReturn(mockMavenProperties); } @@ -376,9 +378,8 @@ public void testGetContainerBuilderWithLayers_correctFiles() setupBuildConfiguration(Paths.get("nonexistent"), AbsoluteUnixPath.get("/app")); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); - Path dependenciesPath = - Paths.get(Resources.getResource("maven/application/dependencies").toURI()); - Path applicationDirectory = Paths.get(Resources.getResource("maven/application").toURI()); + Path dependenciesPath = getResource("maven/application/dependencies"); + Path applicationDirectory = getResource("maven/application"); assertSourcePathsUnordered( ImmutableList.of( testRepository.artifactPathOnDisk("com.test", "dependency", "1.0.0"), @@ -441,7 +442,7 @@ public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - Path outputPath = Paths.get(Resources.getResource("maven/webapp").toURI()); + Path outputPath = getResource("maven/webapp"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); Mockito.when(mockBuild.getDirectory()).thenReturn(outputPath.toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); @@ -522,7 +523,6 @@ public void testGetContainerBuilderWithLayers_jarNonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { // Test when the default packaging is set Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); @@ -567,28 +567,24 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist @Test public void testIsWarProject_WarPackagingIsWar() { Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); - Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); } @Test public void testIsWarProject_GwtAppPackagingIsWar() { Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-app"); - Assert.assertTrue(MojoCommon.isWarProject(mockMavenProject)); } @Test public void testIsWarProject_JarPackagingIsNotWar() { Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); } @Test public void testIsWarProject_GwtLibPackagingIsNotWar() { Mockito.when(mockMavenProject.getPackaging()).thenReturn("gwt-lib"); - Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); } From 077470b31e99ff3e6f47f4a76d0c7dfb3c09d214 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 15:31:35 -0400 Subject: [PATCH 12/20] Add new method --- .../tools/jib/api/JavaContainerBuilder.java | 17 ++++++++++++++++- .../common/JavaContainerBuilderHelper.java | 2 +- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index bb5df8a753..f9517d5d24 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -33,6 +33,7 @@ import java.nio.file.Path; import java.util.ArrayList; import java.util.Arrays; +import java.util.Collections; import java.util.LinkedHashSet; import java.util.List; import java.util.Map.Entry; @@ -246,6 +247,21 @@ public JavaContainerBuilder addDependencies(Path... dependencyFiles) throws IOEx return addDependencies(Arrays.asList(dependencyFiles)); } + /** + * Adds dependency JARs to the image given a root directory. Duplicate JAR filenames are renamed + * with the filesize in order to avoid collisions. + * + * @param dependenciesDirectory the directory containing dependency JARs to add to the image + * @return this + * @throws IOException if adding the layer fails + */ + public JavaContainerBuilder addDependencies(Path dependenciesDirectory) throws IOException { + if (!Files.isDirectory(dependenciesDirectory)) { + return addDependencies(Collections.singletonList(dependenciesDirectory)); + } + return addDependencies(dependenciesDirectory, path -> true); + } + /** * Adds dependency JARs to the image. Duplicate JAR filenames are renamed with the filesize in * order to avoid collisions. @@ -265,7 +281,6 @@ public JavaContainerBuilder addDependencies( .walk() .asList()); } - /** * Adds the contents of a resources directory to the image. * diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index ac690a2d76..fa498b2c72 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -98,7 +98,7 @@ public static JibContainerBuilder fromExplodedWar( javaContainerBuilder.addClasses(webInfClasses, isClassFile); } if (Files.exists(webInfLib)) { - javaContainerBuilder.addDependencies(webInfLib, isDependency); + javaContainerBuilder.addDependencies(webInfLib); } JibContainerBuilder jibContainerBuilder = javaContainerBuilder.toContainerBuilder(); From 4b5a19d803a05b3adaaa8b4725bbfc861f9f19b0 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Thu, 21 Mar 2019 16:18:52 -0400 Subject: [PATCH 13/20] Some feedback --- .../tools/jib/api/JavaContainerBuilder.java | 29 +++++++++---------- .../jib/gradle/GradleProjectProperties.java | 2 +- 2 files changed, 14 insertions(+), 17 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index f9517d5d24..729e162378 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -129,7 +129,7 @@ public static JavaContainerBuilder from(RegistryImage registryImage) { // Keeps track of files to add to the image, by system path private final List addedResources = new ArrayList<>(); private final List addedClasses = new ArrayList<>(); - private final List addedDependencies = new ArrayList<>(); + private final List addedDependencies = new ArrayList<>(); private final List addedOthers = new ArrayList<>(); private AbsoluteUnixPath appRoot = AbsoluteUnixPath.get("/app"); @@ -229,7 +229,7 @@ public JavaContainerBuilder addDependencies(List dependencyFiles) throws I if (!Files.exists(file)) { throw new NoSuchFileException(file.toString()); } - addedDependencies.add(new PathPredicatePair(file, path -> true)); + addedDependencies.add(file); } classpathOrder.add(LayerType.DEPENDENCIES); return this; @@ -248,8 +248,8 @@ public JavaContainerBuilder addDependencies(Path... dependencyFiles) throws IOEx } /** - * Adds dependency JARs to the image given a root directory. Duplicate JAR filenames are renamed - * with the filesize in order to avoid collisions. + * Adds the contents of a dependency JAR directory to the image. Duplicate JAR filenames are + * renamed with the filesize in order to avoid collisions. * * @param dependenciesDirectory the directory containing dependency JARs to add to the image * @return this @@ -263,8 +263,8 @@ public JavaContainerBuilder addDependencies(Path dependenciesDirectory) throws I } /** - * Adds dependency JARs to the image. Duplicate JAR filenames are renamed with the filesize in - * order to avoid collisions. + * Adds the contents of a dependency JAR directory to the image. Duplicate JAR filenames are + * renamed with the filesize in order to avoid collisions. * * @param dependenciesDirectory the directory containing dependency JARs to add to the image * @param pathFilter filter that determines which files (not directories) should be added @@ -461,7 +461,6 @@ public JibContainerBuilder toContainerBuilder() throws IOException { List duplicates = addedDependencies .stream() - .map(entry -> entry.path) .map(Path::getFileName) .map(Path::toString) .collect(Collectors.groupingBy(filename -> filename, Collectors.counting())) @@ -470,24 +469,22 @@ public JibContainerBuilder toContainerBuilder() throws IOException { .filter(entry -> entry.getValue() > 1) .map(Entry::getKey) .collect(Collectors.toList()); - for (PathPredicatePair pathPredicatePair : addedDependencies) { + for (Path path : addedDependencies) { // Add dependencies to layer configuration layerConfigurationsBuilder.addFile( - pathPredicatePair.path.getFileName().toString().contains("SNAPSHOT") + path.getFileName().toString().contains("SNAPSHOT") ? LayerType.SNAPSHOT_DEPENDENCIES : LayerType.DEPENDENCIES, - pathPredicatePair.path, + path, appRoot .resolve(dependenciesDestination) .resolve( - duplicates.contains(pathPredicatePair.path.getFileName().toString()) - ? pathPredicatePair - .path - .getFileName() + duplicates.contains(path.getFileName().toString()) + ? path.getFileName() .toString() - .replaceFirst("\\.jar$", "-" + Files.size(pathPredicatePair.path)) + .replaceFirst("\\.jar$", "-" + Files.size(path)) + ".jar" - : pathPredicatePair.path.getFileName().toString())); + : path.getFileName().toString())); } // Add others to layer configuration diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index 4484cc87a7..96f0fd9721 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -174,7 +174,7 @@ private static boolean isProgressFooterEnabled(Project project) { @Override public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) { try { - if (TaskCommon.getWarTask(project) != null) { + if (isWarProject()) { logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); Path explodedWarPath = GradleProjectProperties.getExplodedWarDirectory(project); return JavaContainerBuilderHelper.fromExplodedWar( From 5332dd9a235ab8cb12b4200544f8a736d0505885 Mon Sep 17 00:00:00 2001 From: Tad Cordle Date: Fri, 22 Mar 2019 13:50:35 -0400 Subject: [PATCH 14/20] Move adding extra directory layer to plugins-common --- .../tools/jib/gradle/BuildDockerTask.java | 7 +- .../tools/jib/gradle/BuildImageTask.java | 7 +- .../cloud/tools/jib/gradle/BuildTarTask.java | 8 +- .../jib/gradle/GradleProjectProperties.java | 56 ++---------- .../jib/gradle/GradleRawConfiguration.java | 13 +++ .../cloud/tools/jib/gradle/TaskCommon.java | 24 +++++ .../gradle/GradleProjectPropertiesTest.java | 87 +++---------------- .../tools/jib/maven/BuildDockerMojo.java | 8 +- .../cloud/tools/jib/maven/BuildImageMojo.java | 8 +- .../cloud/tools/jib/maven/BuildTarMojo.java | 8 +- .../jib/maven/MavenProjectProperties.java | 61 ++++--------- .../jib/maven/MavenRawConfiguration.java | 13 +++ .../jib/maven/MavenProjectPropertiesTest.java | 76 +++------------- .../common/JavaContainerBuilderHelper.java | 20 +---- .../common/PluginConfigurationProcessor.java | 9 ++ .../jib/plugins/common/RawConfiguration.java | 7 ++ .../JavaContainerBuilderHelperTest.java | 20 +---- .../PluginConfigurationProcessorTest.java | 1 + 18 files changed, 120 insertions(+), 313 deletions(-) diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildDockerTask.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildDockerTask.java index b6f0da5614..92c980de00 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildDockerTask.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildDockerTask.java @@ -111,12 +111,7 @@ public void buildDocker() PluginConfigurationProcessor.getAppRootChecked( gradleRawConfiguration, TaskCommon.isWarProject(getProject())); GradleProjectProperties projectProperties = - GradleProjectProperties.getForProject( - getProject(), - getLogger(), - jibExtension.getExtraDirectory().getPath(), - jibExtension.getExtraDirectory().getPermissions(), - appRoot); + GradleProjectProperties.getForProject(getProject(), getLogger(), appRoot); GradleHelpfulSuggestionsBuilder gradleHelpfulSuggestionsBuilder = new GradleHelpfulSuggestionsBuilder(HELPFUL_SUGGESTIONS_PREFIX, jibExtension); diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildImageTask.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildImageTask.java index b0f83d51bb..dec9f1e5f4 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildImageTask.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildImageTask.java @@ -88,12 +88,7 @@ public void buildImage() PluginConfigurationProcessor.getAppRootChecked( gradleRawConfiguration, TaskCommon.isWarProject(getProject())); GradleProjectProperties projectProperties = - GradleProjectProperties.getForProject( - getProject(), - getLogger(), - jibExtension.getExtraDirectory().getPath(), - jibExtension.getExtraDirectory().getPermissions(), - appRoot); + GradleProjectProperties.getForProject(getProject(), getLogger(), appRoot); if (Strings.isNullOrEmpty(jibExtension.getTo().getImage())) { throw new GradleException( diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildTarTask.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildTarTask.java index 0120991465..0968d5c692 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildTarTask.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/BuildTarTask.java @@ -110,13 +110,7 @@ public void buildTar() PluginConfigurationProcessor.getAppRootChecked( gradleRawConfiguration, TaskCommon.isWarProject(getProject())); GradleProjectProperties projectProperties = - GradleProjectProperties.getForProject( - getProject(), - getLogger(), - jibExtension.getExtraDirectory().getPath(), - jibExtension.getExtraDirectory().getPermissions(), - appRoot); - + GradleProjectProperties.getForProject(getProject(), getLogger(), appRoot); GradleHelpfulSuggestionsBuilder gradleHelpfulSuggestionsBuilder = new GradleHelpfulSuggestionsBuilder(HELPFUL_SUGGESTIONS_PREFIX, jibExtension); diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index 96f0fd9721..f4e976037b 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -19,7 +19,6 @@ import com.google.cloud.tools.jib.api.JavaContainerBuilder; import com.google.cloud.tools.jib.api.JibContainerBuilder; import com.google.cloud.tools.jib.api.RegistryImage; -import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEventType; import com.google.cloud.tools.jib.event.events.LogEvent; @@ -41,10 +40,7 @@ import java.nio.file.Files; import java.nio.file.Path; import java.util.ArrayList; -import java.util.HashMap; import java.util.List; -import java.util.Map; -import java.util.Map.Entry; import java.util.Set; import java.util.stream.Collectors; import javax.annotation.Nullable; @@ -76,13 +72,8 @@ class GradleProjectProperties implements ProjectProperties { /** @return a GradleProjectProperties from the given project and logger. */ static GradleProjectProperties getForProject( - Project project, - Logger logger, - Path extraDirectory, - Map permissions, - AbsoluteUnixPath appRoot) { - return new GradleProjectProperties( - project, logger, extraDirectory, convertPermissionsMap(permissions), appRoot); + Project project, Logger logger, AbsoluteUnixPath appRoot) { + return new GradleProjectProperties(project, logger, appRoot); } static Path getExplodedWarDirectory(Project project) { @@ -151,21 +142,12 @@ private static boolean isProgressFooterEnabled(Project project) { private final SingleThreadedExecutor singleThreadedExecutor = new SingleThreadedExecutor(); private final EventHandlers eventHandlers; private final Logger logger; - private final Path extraDirectory; - private final Map permissions; private final AbsoluteUnixPath appRoot; @VisibleForTesting - GradleProjectProperties( - Project project, - Logger logger, - Path extraDirectory, - Map permissions, - AbsoluteUnixPath appRoot) { + GradleProjectProperties(Project project, Logger logger, AbsoluteUnixPath appRoot) { this.project = project; this.logger = logger; - this.extraDirectory = extraDirectory; - this.permissions = permissions; this.appRoot = appRoot; eventHandlers = makeEventHandlers(project, logger, singleThreadedExecutor); @@ -177,8 +159,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage if (isWarProject()) { logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); Path explodedWarPath = GradleProjectProperties.getExplodedWarDirectory(project); - return JavaContainerBuilderHelper.fromExplodedWar( - baseImage, explodedWarPath, appRoot, extraDirectory, permissions); + return JavaContainerBuilderHelper.fromExplodedWar(baseImage, explodedWarPath, appRoot); } JavaPluginConvention javaPluginConvention = @@ -222,15 +203,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage .map(File::toPath) .collect(Collectors.toList())); - JibContainerBuilder jibContainerBuilder = javaContainerBuilder.toContainerBuilder(); - - // Adds all the extra files. - if (Files.exists(extraDirectory)) { - jibContainerBuilder.addLayer( - JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( - extraDirectory, permissions)); - } - return jibContainerBuilder; + return javaContainerBuilder.toContainerBuilder(); } catch (IOException ex) { throw new GradleException("Obtaining project build output files failed", ex); @@ -340,23 +313,4 @@ public int getMajorJavaVersion() { } return Integer.valueOf(version.getMajorVersion()); } - - /** - * Validates and converts a {@code String->String} file-path-to-file-permissions map to an - * equivalent {@code AbsoluteUnixPath->FilePermission} map. - * - * @param stringMap the map to convert (example entry: {@code "/path/on/container" -> "755"}) - * @return the converted map - */ - @VisibleForTesting - static Map convertPermissionsMap( - Map stringMap) { - Map permissionsMap = new HashMap<>(); - for (Entry entry : stringMap.entrySet()) { - AbsoluteUnixPath key = AbsoluteUnixPath.get(entry.getKey()); - FilePermissions value = FilePermissions.fromOctalString(entry.getValue()); - permissionsMap.put(key, value); - } - return permissionsMap; - } } diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleRawConfiguration.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleRawConfiguration.java index 4be98543f2..25d28dbd5d 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleRawConfiguration.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleRawConfiguration.java @@ -16,9 +16,12 @@ package com.google.cloud.tools.jib.gradle; +import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.image.ImageFormat; import com.google.cloud.tools.jib.plugins.common.AuthProperty; import com.google.cloud.tools.jib.plugins.common.RawConfiguration; +import java.nio.file.Path; import java.util.List; import java.util.Map; import java.util.Optional; @@ -141,4 +144,14 @@ public ImageFormat getImageFormat() { public Optional getProperty(String propertyName) { return Optional.ofNullable(System.getProperty(propertyName)); } + + @Override + public Path getExtraDirectory() { + return jibExtension.getExtraDirectory().getPath(); + } + + @Override + public Map getExtraDirectoryPermissions() { + return TaskCommon.convertPermissionsMap(jibExtension.getExtraDirectory().getPermissions()); + } } diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/TaskCommon.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/TaskCommon.java index 65f47d4ccc..3464a0d197 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/TaskCommon.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/TaskCommon.java @@ -17,6 +17,11 @@ package com.google.cloud.tools.jib.gradle; import com.google.api.client.http.HttpTransport; +import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; +import com.google.common.annotations.VisibleForTesting; +import java.util.HashMap; +import java.util.Map; import java.util.logging.Level; import javax.annotation.Nullable; import org.gradle.api.Project; @@ -62,5 +67,24 @@ static void disableHttpLogging() { java.util.logging.Logger.getLogger(HttpTransport.class.getName()).setLevel(Level.OFF); } + /** + * Validates and converts a {@code String->String} file-path-to-file-permissions map to an + * equivalent {@code AbsoluteUnixPath->FilePermission} map. + * + * @param stringMap the map to convert (example entry: {@code "/path/on/container" -> "755"}) + * @return the converted map + */ + @VisibleForTesting + static Map convertPermissionsMap( + Map stringMap) { + Map permissionsMap = new HashMap<>(); + for (Map.Entry entry : stringMap.entrySet()) { + AbsoluteUnixPath key = AbsoluteUnixPath.get(entry.getKey()); + FilePermissions value = FilePermissions.fromOctalString(entry.getValue()); + permissionsMap.put(key, value); + } + return permissionsMap; + } + private TaskCommon() {} } diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index 580fca8667..15295b8c4e 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -114,7 +114,6 @@ private static class ContainerBuilderLayers { private final List classesLayerEntries; private final List dependenciesLayerEntries; private final List snapshotsLayerEntries; - private final List extraFilesLayerEntries; private ContainerBuilderLayers(BuildConfiguration configuration) { resourcesLayerEntries = @@ -124,8 +123,6 @@ private ContainerBuilderLayers(BuildConfiguration configuration) { getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); snapshotsLayerEntries = getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - extraFilesLayerEntries = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); } } @@ -179,8 +176,6 @@ private static Path getResource(String path) throws URISyntaxException { @Mock private TaskContainer taskContainer; @Mock private War war; - private Path extraFilesDirectory; - private Manifest manifest; private GradleProjectProperties gradleProjectProperties; @@ -223,15 +218,8 @@ public void setup() throws URISyntaxException, IOException { getResource("gradle/webapp").resolve("jib-exploded-war/WEB-INF/classes/empty_dir"); Files.createDirectories(emptyDirectory); - extraFilesDirectory = getResource("core/layer"); - gradleProjectProperties = - new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - ImmutableMap.of(), - AbsoluteUnixPath.get("/app")); + new GradleProjectProperties(mockProject, mockLogger, AbsoluteUnixPath.get("/app")); } @Test @@ -288,12 +276,11 @@ public void testConvertPermissionsMap() { FilePermissions.fromOctalString("123"), AbsoluteUnixPath.get("/test/file2"), FilePermissions.fromOctalString("456")), - GradleProjectProperties.convertPermissionsMap( + TaskCommon.convertPermissionsMap( ImmutableMap.of("/test/folder/file1", "123", "/test/file2", "456"))); try { - GradleProjectProperties.convertPermissionsMap( - ImmutableMap.of("a path", "not valid permission")); + TaskCommon.convertPermissionsMap(ImmutableMap.of("a path", "not valid permission")); Assert.fail(); } catch (IllegalArgumentException ignored) { // pass @@ -336,8 +323,7 @@ public void testGetMajorJavaVersion_jvm11() { public void testGetContainerBuilderWithLayers_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - setupBuildConfiguration(Paths.get("nonexistent/path"), "/app"); + BuildConfiguration configuration = setupBuildConfiguration("/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); Path applicationDirectory = getResource("gradle/application"); @@ -365,7 +351,6 @@ public void testGetContainerBuilderWithLayers_correctFiles() applicationDirectory.resolve("classes/HelloWorld.class"), applicationDirectory.resolve("classes/some.class")), layers.classesLayerEntries.get(0).getLayerEntries()); - Assert.assertEquals(0, layers.extraFilesLayerEntries.size()); } @Test @@ -378,27 +363,10 @@ public void testGetContainerBuilderWithLayers_noClassesFiles() Mockito.verify(mockLogger).warn("No classes files were found - did you compile your project?"); } - @Test - public void testGetContainerBuilderWithLayers_extraFiles() - throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/app"); - assertSourcePathsUnordered( - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")), - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()) - .get(0) - .getLayerEntries()); - } - @Test public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); + BuildConfiguration configuration = setupBuildConfiguration("/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( @@ -422,16 +390,13 @@ public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() assertExtractionPathsUnordered( Arrays.asList("/my/app/classes/HelloWorld.class", "/my/app/classes/some.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test public void testGetContainerBuilderWithLayers_defaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_APP_ROOT); + setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_APP_ROOT); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Arrays.asList( @@ -452,9 +417,6 @@ public void testGetContainerBuilderWithLayers_defaultAppRoot() assertExtractionPathsUnordered( Arrays.asList("/app/classes/HelloWorld.class", "/app/classes/some.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -464,7 +426,7 @@ public void testGetContainerBuilderWithLayers_war() Path webAppDirectory = getResource("gradle/webapp"); setUpWarProject(webAppDirectory); - BuildConfiguration configuration = setupBuildConfiguration(extraFilesDirectory, "/my/app"); + BuildConfiguration configuration = setupBuildConfiguration("/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of( @@ -494,15 +456,6 @@ public void testGetContainerBuilderWithLayers_war() webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package"), webAppDirectory.resolve("jib-exploded-war/WEB-INF/classes/package/Other.class")), layers.classesLayerEntries.get(0).getLayerEntries()); - assertSourcePathsUnordered( - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), @@ -530,9 +483,6 @@ public void testGetContainerBuilderWithLayers_war() "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -542,7 +492,7 @@ public void testGetContainerBuilderWithLayers_defaultWebAppRoot() setUpWarProject(getResource("gradle/webapp")); BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); + setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertExtractionPathsUnordered( Collections.singletonList("/jetty/webapps/ROOT/WEB-INF/lib/dependency-1.0.0.jar"), @@ -570,9 +520,6 @@ public void testGetContainerBuilderWithLayers_defaultWebAppRoot() "/jetty/webapps/ROOT/WEB-INF/classes/package", "/jetty/webapps/ROOT/WEB-INF/classes/package/Other.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -580,8 +527,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); setUpWarProject(temporaryFolder.getRoot().toPath()); - setupBuildConfiguration( - extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass + setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass } @Test @@ -589,8 +535,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); setUpWarProject(temporaryFolder.getRoot().toPath()); - setupBuildConfiguration( - extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass + setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass } @Test @@ -598,18 +543,12 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war"); setUpWarProject(temporaryFolder.getRoot().toPath()); - setupBuildConfiguration( - extraFilesDirectory, JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass + setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_WEB_APP_ROOT); // should pass } - private BuildConfiguration setupBuildConfiguration(Path extraFilesDirectory, String appRoot) + private BuildConfiguration setupBuildConfiguration(String appRoot) throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { - return new GradleProjectProperties( - mockProject, - mockLogger, - extraFilesDirectory, - Collections.emptyMap(), - AbsoluteUnixPath.get(appRoot)) + return new GradleProjectProperties(mockProject, mockLogger, AbsoluteUnixPath.get(appRoot)) .getContainerBuilderWithLayers(RegistryImage.named("base")) .toBuildConfiguration( Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildDockerMojo.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildDockerMojo.java index ae0ae39ea4..7bec779dc2 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildDockerMojo.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildDockerMojo.java @@ -97,13 +97,7 @@ public void execute() throws MojoExecutionException, MojoFailureException { PluginConfigurationProcessor.getAppRootChecked( mavenRawConfiguration, MojoCommon.isWarProject(getProject())); MavenProjectProperties projectProperties = - MavenProjectProperties.getForProject( - getProject(), - getSession(), - getLog(), - MojoCommon.getExtraDirectoryPath(this), - MojoCommon.convertPermissionsList(getExtraDirectoryPermissions()), - appRoot); + MavenProjectProperties.getForProject(getProject(), getSession(), getLog(), appRoot); EventDispatcher eventDispatcher = new DefaultEventDispatcher(projectProperties.getEventHandlers()); diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildImageMojo.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildImageMojo.java index 2a0637fb91..467e065883 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildImageMojo.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildImageMojo.java @@ -94,13 +94,7 @@ public void execute() throws MojoExecutionException, MojoFailureException { PluginConfigurationProcessor.getAppRootChecked( mavenRawConfiguration, MojoCommon.isWarProject(getProject())); MavenProjectProperties projectProperties = - MavenProjectProperties.getForProject( - getProject(), - getSession(), - getLog(), - MojoCommon.getExtraDirectoryPath(this), - MojoCommon.convertPermissionsList(getExtraDirectoryPermissions()), - appRoot); + MavenProjectProperties.getForProject(getProject(), getSession(), getLog(), appRoot); EventDispatcher eventDispatcher = new DefaultEventDispatcher(projectProperties.getEventHandlers()); diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildTarMojo.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildTarMojo.java index 55ecf4b4c9..246f89f0fd 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildTarMojo.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/BuildTarMojo.java @@ -70,13 +70,7 @@ public void execute() throws MojoExecutionException, MojoFailureException { PluginConfigurationProcessor.getAppRootChecked( mavenRawConfiguration, MojoCommon.isWarProject(getProject())); MavenProjectProperties projectProperties = - MavenProjectProperties.getForProject( - getProject(), - getSession(), - getLog(), - MojoCommon.getExtraDirectoryPath(this), - MojoCommon.convertPermissionsList(getExtraDirectoryPermissions()), - appRoot); + MavenProjectProperties.getForProject(getProject(), getSession(), getLog(), appRoot); EventDispatcher eventDispatcher = new DefaultEventDispatcher(projectProperties.getEventHandlers()); diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index 661674042e..2fe340eaa9 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -19,7 +19,6 @@ import com.google.cloud.tools.jib.api.JavaContainerBuilder; import com.google.cloud.tools.jib.api.JibContainerBuilder; import com.google.cloud.tools.jib.api.RegistryImage; -import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEventType; import com.google.cloud.tools.jib.event.events.LogEvent; @@ -38,10 +37,8 @@ import com.google.common.collect.ImmutableList; import java.io.File; import java.io.IOException; -import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; -import java.util.Map; import java.util.function.Predicate; import java.util.stream.Collectors; import javax.annotation.Nullable; @@ -72,19 +69,12 @@ public class MavenProjectProperties implements ProjectProperties { * @param project the {@link MavenProject} for the plugin. * @param session the {@link MavenSession} for the plugin. * @param log the Maven {@link Log} to log messages during Jib execution - * @param extraDirectory path to the directory for the extra files layer - * @param permissions map from path on container to file permissions for extra-layer files * @param appRoot root directory in the image where the app will be placed * @return a MavenProjectProperties from the given project and logger. */ static MavenProjectProperties getForProject( - MavenProject project, - MavenSession session, - Log log, - Path extraDirectory, - Map permissions, - AbsoluteUnixPath appRoot) { - return new MavenProjectProperties(project, session, log, extraDirectory, permissions, appRoot); + MavenProject project, MavenSession session, Log log, AbsoluteUnixPath appRoot) { + return new MavenProjectProperties(project, session, log, appRoot); } /** @@ -194,21 +184,12 @@ static int getVersionFromString(String versionString) { private final MavenProject project; private final SingleThreadedExecutor singleThreadedExecutor = new SingleThreadedExecutor(); private final EventHandlers eventHandlers; - private final Path extraDirectory; - private final Map permissions; private final AbsoluteUnixPath appRoot; @VisibleForTesting MavenProjectProperties( - MavenProject project, - MavenSession session, - Log log, - Path extraDirectory, - Map permissions, - AbsoluteUnixPath appRoot) { + MavenProject project, MavenSession session, Log log, AbsoluteUnixPath appRoot) { this.project = project; - this.extraDirectory = extraDirectory; - this.permissions = permissions; this.appRoot = appRoot; eventHandlers = makeEventHandlers(session, log, singleThreadedExecutor); } @@ -220,35 +201,25 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage if (MojoCommon.isWarProject(project)) { Path explodedWarPath = Paths.get(project.getBuild().getDirectory()).resolve(project.getBuild().getFinalName()); - return JavaContainerBuilderHelper.fromExplodedWar( - baseImage, explodedWarPath, appRoot, extraDirectory, permissions); + return JavaContainerBuilderHelper.fromExplodedWar(baseImage, explodedWarPath, appRoot); } Path classesOutputDirectory = Paths.get(project.getBuild().getOutputDirectory()); Predicate isClassFile = path -> path.getFileName().toString().endsWith(".class"); // Add dependencies, resources, and classes - JibContainerBuilder jibContainerBuilder = - JavaContainerBuilder.from(baseImage) - .setAppRoot(appRoot) - .addResources(classesOutputDirectory, isClassFile.negate()) - .addClasses(classesOutputDirectory, isClassFile) - .addDependencies( - project - .getArtifacts() - .stream() - .map(Artifact::getFile) - .map(File::toPath) - .collect(Collectors.toList())) - .toContainerBuilder(); - - // Adds all the extra files. - if (Files.exists(extraDirectory)) { - jibContainerBuilder.addLayer( - JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( - extraDirectory, permissions)); - } - return jibContainerBuilder; + return JavaContainerBuilder.from(baseImage) + .setAppRoot(appRoot) + .addResources(classesOutputDirectory, isClassFile.negate()) + .addClasses(classesOutputDirectory, isClassFile) + .addDependencies( + project + .getArtifacts() + .stream() + .map(Artifact::getFile) + .map(File::toPath) + .collect(Collectors.toList())) + .toContainerBuilder(); } catch (IOException ex) { throw new IOException( diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenRawConfiguration.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenRawConfiguration.java index 0b9c901de6..a94313f4e5 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenRawConfiguration.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenRawConfiguration.java @@ -16,9 +16,12 @@ package com.google.cloud.tools.jib.maven; +import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.image.ImageFormat; import com.google.cloud.tools.jib.plugins.common.AuthProperty; import com.google.cloud.tools.jib.plugins.common.RawConfiguration; +import java.nio.file.Path; import java.util.List; import java.util.Map; import java.util.Optional; @@ -146,4 +149,14 @@ public ImageFormat getImageFormat() { public Optional getProperty(String propertyName) { return Optional.ofNullable(jibPluginConfiguration.getProperty(propertyName)); } + + @Override + public Path getExtraDirectory() { + return MojoCommon.getExtraDirectoryPath(jibPluginConfiguration); + } + + @Override + public Map getExtraDirectoryPermissions() { + return MojoCommon.convertPermissionsList(jibPluginConfiguration.getExtraDirectoryPermissions()); + } } diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 568712cf3b..f68f9b9683 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -26,7 +26,6 @@ import com.google.cloud.tools.jib.image.InvalidImageReferenceException; import com.google.cloud.tools.jib.image.LayerEntry; import com.google.common.collect.ImmutableList; -import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; import com.google.common.io.Resources; import com.google.common.util.concurrent.MoreExecutors; @@ -71,7 +70,6 @@ private static class ContainerBuilderLayers { private final List classesLayerEntries; private final List dependenciesLayerEntries; private final List snapshotsLayerEntries; - private final List extraFilesLayerEntries; private ContainerBuilderLayers(BuildConfiguration configuration) { resourcesLayerEntries = getLayerEntriesByName(configuration, LayerType.RESOURCES.getName()); @@ -80,8 +78,6 @@ private ContainerBuilderLayers(BuildConfiguration configuration) { getLayerEntriesByName(configuration, LayerType.DEPENDENCIES.getName()); snapshotsLayerEntries = getLayerEntriesByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - extraFilesLayerEntries = - getLayerEntriesByName(configuration, LayerType.EXTRA_FILES.getName()); } } @@ -143,9 +139,6 @@ private static void assertNonDefaultAppRoot(BuildConfiguration configuration) { "/my/app/classes/package/some.class", "/my/app/classes/some.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } private static Path getResource(String path) throws URISyntaxException { @@ -174,19 +167,13 @@ private static Path getResource(String path) throws URISyntaxException { @Mock private Xpp3Dom compilerRelease; private MavenProjectProperties mavenProjectProperties; - private Path extraFilesDirectory; @Before public void setup() throws IOException, URISyntaxException { Mockito.when(mockMavenSession.getRequest()).thenReturn(mockMavenRequest); mavenProjectProperties = new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - ImmutableMap.of(), - AbsoluteUnixPath.get("/app")); + mockMavenProject, mockMavenSession, mockLog, AbsoluteUnixPath.get("/app")); jarPluginConfiguration = new Xpp3Dom(""); archive = new Xpp3Dom("archive"); manifest = new Xpp3Dom("manifest"); @@ -216,8 +203,6 @@ public void setup() throws IOException, URISyntaxException { getResource("maven/webapp").resolve("final-name/WEB-INF/classes/empty_dir"); Files.createDirectories(emptyDirectory); - extraFilesDirectory = getResource("core/layer"); - Mockito.when(mockMavenProject.getProperties()).thenReturn(mockMavenProperties); } @@ -374,8 +359,7 @@ public void isProgressFooterEnabled() { public void testGetContainerBuilderWithLayers_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - setupBuildConfiguration(Paths.get("nonexistent"), AbsoluteUnixPath.get("/app")); + BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/app")); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); Path dependenciesPath = getResource("maven/application/dependencies"); @@ -412,29 +396,10 @@ public void testGetContainerBuilderWithLayers_correctFiles() layers.classesLayerEntries.get(0).getLayerEntries()); } - @Test - public void testGetContainerBuilderWithLayers_extraFiles() - throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/app")); - assertSourcePathsUnordered( - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")), - getLayerEntriesByName(configuration, LayerType.EXTRA_FILES.getName()) - .get(0) - .getLayerEntries()); - } - @Test public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { - BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); + BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); } @@ -447,8 +412,7 @@ public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() Mockito.when(mockBuild.getDirectory()).thenReturn(outputPath.toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); + BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); assertSourcePathsUnordered( ImmutableList.of(outputPath.resolve("final-name/WEB-INF/lib/dependency-1.0.0.jar")), @@ -477,15 +441,6 @@ public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() outputPath.resolve("final-name/WEB-INF/classes/package"), outputPath.resolve("final-name/WEB-INF/classes/package/Other.class")), layers.classesLayerEntries.get(0).getLayerEntries()); - assertSourcePathsUnordered( - ImmutableList.of( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), @@ -513,9 +468,6 @@ public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), layers.classesLayerEntries.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - layers.extraFilesLayerEntries.get(0).getLayerEntries()); } @Test @@ -523,8 +475,7 @@ public void testGetContainerBuilderWithLayers_jarNonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { // Test when the default packaging is set Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); - BuildConfiguration configuration = - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); + BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); } @@ -537,7 +488,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass + setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -549,7 +500,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass + setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -561,7 +512,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist .thenReturn(temporaryFolder.getRoot().toPath().toString()); Mockito.when(mockBuild.getFinalName()).thenReturn("final-name"); - setupBuildConfiguration(extraFilesDirectory, AbsoluteUnixPath.get("/my/app")); // should pass + setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); // should pass } @Test @@ -588,16 +539,9 @@ public void testIsWarProject_GwtLibPackagingIsNotWar() { Assert.assertFalse(MojoCommon.isWarProject(mockMavenProject)); } - private BuildConfiguration setupBuildConfiguration( - Path extraFilesDirectory, AbsoluteUnixPath appRoot) + private BuildConfiguration setupBuildConfiguration(AbsoluteUnixPath appRoot) throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { - return new MavenProjectProperties( - mockMavenProject, - mockMavenSession, - mockLog, - extraFilesDirectory, - Collections.emptyMap(), - appRoot) + return new MavenProjectProperties(mockMavenProject, mockMavenSession, mockLog, appRoot) .getContainerBuilderWithLayers(RegistryImage.named("base")) .toBuildConfiguration( Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index fa498b2c72..3c9a7d9bfc 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -65,18 +65,11 @@ public static LayerConfiguration extraDirectoryLayerConfiguration( * @param baseImage the base image of the container * @param explodedWar the exploded WAR directory * @param appRoot root directory in the image where the app will be placed - * @param extraFilesDirectory path to the source directory for the extra files layer - * @param extraDirectoryPermissions map from path on container to file permissions * @return {@link JibContainerBuilder} containing the layers for the exploded WAR * @throws IOException if adding layer contents fails */ public static JibContainerBuilder fromExplodedWar( - RegistryImage baseImage, - Path explodedWar, - AbsoluteUnixPath appRoot, - Path extraFilesDirectory, - Map extraDirectoryPermissions) - throws IOException { + RegistryImage baseImage, Path explodedWar, AbsoluteUnixPath appRoot) throws IOException { Path webInfLib = explodedWar.resolve("WEB-INF/lib"); Path webInfClasses = explodedWar.resolve("WEB-INF/classes"); Predicate isDependency = path -> path.startsWith(webInfLib); @@ -100,16 +93,7 @@ public static JibContainerBuilder fromExplodedWar( if (Files.exists(webInfLib)) { javaContainerBuilder.addDependencies(webInfLib); } - JibContainerBuilder jibContainerBuilder = javaContainerBuilder.toContainerBuilder(); - - // Adds all the extra files. - if (Files.exists(extraFilesDirectory)) { - jibContainerBuilder.addLayer( - JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( - extraFilesDirectory, extraDirectoryPermissions)); - } - - return jibContainerBuilder; + return javaContainerBuilder.toContainerBuilder(); } private JavaContainerBuilderHelper() {} diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java index 3606a2a9dc..2c9e997995 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java @@ -38,6 +38,7 @@ import com.google.common.base.Verify; import java.io.FileNotFoundException; import java.io.IOException; +import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; import java.time.Instant; @@ -204,6 +205,14 @@ static PluginConfigurationProcessor processCommonConfiguration( jibContainerBuilder.setCreationTime(Instant.now()); } + // Adds all the extra files. + if (Files.exists(rawConfiguration.getExtraDirectory())) { + jibContainerBuilder.addLayer( + JavaContainerBuilderHelper.extraDirectoryLayerConfiguration( + rawConfiguration.getExtraDirectory(), + rawConfiguration.getExtraDirectoryPermissions())); + } + PluginConfigurationProcessor.configureContainerizer( containerizer, rawConfiguration, projectProperties); diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/RawConfiguration.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/RawConfiguration.java index 1d55b9fd8c..a2fd77aad7 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/RawConfiguration.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/RawConfiguration.java @@ -16,7 +16,10 @@ package com.google.cloud.tools.jib.plugins.common; +import com.google.cloud.tools.jib.configuration.FilePermissions; +import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; import com.google.cloud.tools.jib.image.ImageFormat; +import java.nio.file.Path; import java.util.List; import java.util.Map; import java.util.Optional; @@ -70,4 +73,8 @@ public interface RawConfiguration { ImageFormat getImageFormat(); Optional getProperty(String propertyName); + + Path getExtraDirectory(); + + Map getExtraDirectoryPermissions(); } diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java index c70bc850b8..826629120d 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java @@ -108,11 +108,7 @@ public void testFromExplodedWar() BuildConfiguration configuration = JavaContainerBuilderHelper.fromExplodedWar( - RegistryImage.named("base"), - temporaryExplodedWar, - AbsoluteUnixPath.get("/my/app"), - extraFilesDirectory, - Collections.emptyMap()) + RegistryImage.named("base"), temporaryExplodedWar, AbsoluteUnixPath.get("/my/app")) .toBuildConfiguration( Containerizer.to(RegistryImage.named("target")), MoreExecutors.newDirectExecutorService()); @@ -125,8 +121,6 @@ public void testFromExplodedWar() getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); List snapshotsLayerConfigurations = getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); - List extraFilesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.EXTRA_FILES.getName()); assertSourcePathsUnordered( Collections.singletonList(temporaryExplodedWar.resolve("WEB-INF/lib/dependency-1.0.0.jar")), @@ -155,15 +149,6 @@ public void testFromExplodedWar() temporaryExplodedWar.resolve("WEB-INF/classes/package"), temporaryExplodedWar.resolve("WEB-INF/classes/package/Other.class")), classesLayerConfigurations.get(0).getLayerEntries()); - assertSourcePathsUnordered( - Arrays.asList( - extraFilesDirectory.resolve("a"), - extraFilesDirectory.resolve("a/b"), - extraFilesDirectory.resolve("a/b/bar"), - extraFilesDirectory.resolve("c"), - extraFilesDirectory.resolve("c/cat"), - extraFilesDirectory.resolve("foo")), - extraFilesLayerConfigurations.get(0).getLayerEntries()); assertExtractionPathsUnordered( Collections.singletonList("/my/app/WEB-INF/lib/dependency-1.0.0.jar"), @@ -191,8 +176,5 @@ public void testFromExplodedWar() "/my/app/WEB-INF/classes/package", "/my/app/WEB-INF/classes/package/Other.class"), classesLayerConfigurations.get(0).getLayerEntries()); - assertExtractionPathsUnordered( - Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), - extraFilesLayerConfigurations.get(0).getLayerEntries()); } } diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java index 1fa3dc6b0d..595bbce9c1 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java @@ -69,6 +69,7 @@ public void setUp() throws IOException, InvalidImageReferenceException { Mockito.when(rawConfiguration.getFromAuth()).thenReturn(authProperty); Mockito.when(rawConfiguration.getEntrypoint()).thenReturn(Optional.empty()); Mockito.when(rawConfiguration.getAppRoot()).thenReturn("/app"); + Mockito.when(rawConfiguration.getExtraDirectory()).thenReturn(Paths.get("nonexistent/path")); Mockito.when(projectProperties.getToolName()).thenReturn("tool"); Mockito.when(projectProperties.getMainClassFromJar()).thenReturn("java.lang.Object"); From 29d62e0f601e809fa2ac6cebd8263067f484331d Mon Sep 17 00:00:00 2001 From: Tad Cordle Date: Fri, 22 Mar 2019 14:49:48 -0400 Subject: [PATCH 15/20] Re-add extra directory layer test --- .../PluginConfigurationProcessorTest.java | 72 +++++++++++++++++++ 1 file changed, 72 insertions(+) diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java index 595bbce9c1..de1f4af95f 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java @@ -23,6 +23,7 @@ import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.configuration.BuildConfiguration; import com.google.cloud.tools.jib.configuration.CacheDirectoryCreationException; +import com.google.cloud.tools.jib.configuration.FilePermissions; import com.google.cloud.tools.jib.event.EventHandlers; import com.google.cloud.tools.jib.event.JibEventType; import com.google.cloud.tools.jib.event.events.LogEvent; @@ -30,14 +31,21 @@ import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; import com.google.cloud.tools.jib.image.ImageReference; import com.google.cloud.tools.jib.image.InvalidImageReferenceException; +import com.google.cloud.tools.jib.image.LayerEntry; +import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableSet; +import com.google.common.io.Resources; import java.io.IOException; +import java.net.URISyntaxException; import java.nio.file.Path; import java.nio.file.Paths; import java.util.Arrays; import java.util.Collections; +import java.util.List; import java.util.Optional; import java.util.function.Consumer; +import java.util.function.Function; +import java.util.stream.Collectors; import org.junit.Assert; import org.junit.Before; import org.junit.Test; @@ -57,6 +65,24 @@ private static BuildConfiguration getBuildConfiguration(JibContainerBuilder jibC jibContainerBuilder, Containerizer.to(RegistryImage.named("ignored"))); } + private static void assertLayerEntriesUnordered( + List expectedPaths, List entries, Function fieldSelector) { + List expected = expectedPaths.stream().sorted().collect(Collectors.toList()); + List actual = entries.stream().map(fieldSelector).sorted().collect(Collectors.toList()); + Assert.assertEquals(expected, actual); + } + + private static void assertSourcePathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered(expectedPaths, entries, LayerEntry::getSourceFile); + } + + private static void assertExtractionPathsUnordered( + List expectedPaths, List entries) { + assertLayerEntriesUnordered( + expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); + } + @Mock private RawConfiguration rawConfiguration; @Mock private ProjectProperties projectProperties; @Mock private Containerizer containerizer; @@ -115,6 +141,52 @@ public void testPluginConfigurationProcessor_defaults() Mockito.verify(logger, Mockito.never()).accept(Mockito.argThat(isLogWarn)); } + @Test + public void testPluginConfigurationProcessor_extraDirectory() + throws URISyntaxException, InferredAuthRetrievalException, InvalidContainerVolumeException, + MainClassInferenceException, InvalidAppRootException, IOException, + IncompatibleBaseImageJavaVersionException, InvalidWorkingDirectoryException, + InvalidImageReferenceException, CacheDirectoryCreationException { + Path extraDirectory = Paths.get(Resources.getResource("core/layer").toURI()); + Mockito.when(rawConfiguration.getExtraDirectory()).thenReturn(extraDirectory); + Mockito.when(rawConfiguration.getExtraDirectoryPermissions()) + .thenReturn( + ImmutableMap.of(AbsoluteUnixPath.get("/foo"), FilePermissions.fromOctalString("123"))); + + PluginConfigurationProcessor processor = createPluginConfigurationProcessor(); + BuildConfiguration buildConfiguration = + getBuildConfiguration(processor.getJibContainerBuilder()); + List extraFiles = + buildConfiguration + .getLayerConfigurations() + .stream() + .filter(layer -> layer.getName().equals("extra files")) + .collect(Collectors.toList()) + .get(0) + .getLayerEntries(); + + assertSourcePathsUnordered( + Arrays.asList( + extraDirectory.resolve("a"), + extraDirectory.resolve("a/b"), + extraDirectory.resolve("a/b/bar"), + extraDirectory.resolve("c"), + extraDirectory.resolve("c/cat"), + extraDirectory.resolve("foo")), + extraFiles); + assertExtractionPathsUnordered( + Arrays.asList("/a", "/a/b", "/a/b/bar", "/c", "/c/cat", "/foo"), extraFiles); + + Optional fooEntry = + extraFiles + .stream() + .filter( + layerEntry -> layerEntry.getExtractionPath().equals(AbsoluteUnixPath.get("/foo"))) + .findFirst(); + Assert.assertTrue(fooEntry.isPresent()); + Assert.assertEquals("123", fooEntry.get().getPermissions().toOctalString()); + } + @Test public void testPluginConfigurationProcessor_cacheDirectorySystemProperties() throws InferredAuthRetrievalException, InvalidContainerVolumeException, From de8bc490586002d5aa88e606d7caeb47be9b65e4 Mon Sep 17 00:00:00 2001 From: Tad Cordle Date: Fri, 22 Mar 2019 14:57:02 -0400 Subject: [PATCH 16/20] Reduce unnecessary changes --- .../cloud/tools/jib/api/JavaContainerBuilder.java | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index 729e162378..fd30d1f6e1 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -469,22 +469,22 @@ public JibContainerBuilder toContainerBuilder() throws IOException { .filter(entry -> entry.getValue() > 1) .map(Entry::getKey) .collect(Collectors.toList()); - for (Path path : addedDependencies) { + for (Path file : addedDependencies) { // Add dependencies to layer configuration layerConfigurationsBuilder.addFile( - path.getFileName().toString().contains("SNAPSHOT") + file.getFileName().toString().contains("SNAPSHOT") ? LayerType.SNAPSHOT_DEPENDENCIES : LayerType.DEPENDENCIES, - path, + file, appRoot .resolve(dependenciesDestination) .resolve( - duplicates.contains(path.getFileName().toString()) - ? path.getFileName() + duplicates.contains(file.getFileName().toString()) + ? file.getFileName() .toString() - .replaceFirst("\\.jar$", "-" + Files.size(path)) + .replaceFirst("\\.jar$", "-" + Files.size(file)) + ".jar" - : path.getFileName().toString())); + : file.getFileName().toString())); } // Add others to layer configuration From c59611b9fd74bc38a21dcf06e52fa6e9f6268261 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Mon, 25 Mar 2019 16:31:46 -0400 Subject: [PATCH 17/20] Feedback --- .../tools/jib/frontend/MainClassFinder.java | 4 ++-- .../jib/gradle/GradleProjectProperties.java | 19 +++++++++++-------- .../jib/maven/MavenProjectProperties.java | 9 ++++++--- .../jib/plugins/common/ProjectProperties.java | 4 ++-- 4 files changed, 21 insertions(+), 15 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/MainClassFinder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/MainClassFinder.java index 7a28b4414c..55313079ed 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/MainClassFinder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/frontend/MainClassFinder.java @@ -146,8 +146,8 @@ public MethodVisitor visitMethod( * @param files the files to check * @param eventDispatcher used for dispatching log events. */ - public MainClassFinder(ImmutableList files, EventDispatcher eventDispatcher) { - this.files = files; + public MainClassFinder(List files, EventDispatcher eventDispatcher) { + this.files = ImmutableList.copyOf(files); this.eventDispatcher = eventDispatcher; } diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index f4e976037b..16d8e46949 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -185,12 +185,10 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage } // Adds class files - for (File classesOutputDirectory : classesOutputDirectories.filter(File::exists)) { - if (classesOutputDirectory.exists()) { - javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); - } + for (File classesOutputDirectory : classesOutputDirectories) { + javaContainerBuilder.addClasses(classesOutputDirectory.toPath()); } - if (classesOutputDirectories.filter(File::exists).isEmpty()) { + if (classesOutputDirectories.isEmpty()) { logger.warn("No classes files were found - did you compile your project?"); } @@ -211,15 +209,20 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage } @Override - public ImmutableList getClassFiles() throws IOException { + public List getClassFiles() throws IOException { // TODO: Consolidate with getContainerBuilderWithLayers JavaPluginConvention javaPluginConvention = project.getConvention().getPlugin(JavaPluginConvention.class); SourceSet mainSourceSet = javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); - FileCollection classesOutputDirectories = mainSourceSet.getOutput().getClassesDirs(); + FileCollection classesOutputDirectories = + mainSourceSet.getOutput().getClassesDirs().filter(File::exists); ImmutableList.Builder classFiles = ImmutableList.builder(); for (File classesOutputDirectory : classesOutputDirectories) { - classFiles.addAll(new DirectoryWalker(classesOutputDirectory.toPath()).walk().asList()); + classFiles.addAll( + new DirectoryWalker(classesOutputDirectory.toPath()) + .filter(path -> path.getFileName().endsWith(".class")) + .walk() + .asList()); } return classFiles.build(); } diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index 2fe340eaa9..979127cbf4 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -34,11 +34,11 @@ import com.google.cloud.tools.jib.plugins.common.logging.ProgressDisplayGenerator; import com.google.cloud.tools.jib.plugins.common.logging.SingleThreadedExecutor; import com.google.common.annotations.VisibleForTesting; -import com.google.common.collect.ImmutableList; import java.io.File; import java.io.IOException; import java.nio.file.Path; import java.nio.file.Paths; +import java.util.List; import java.util.function.Predicate; import java.util.stream.Collectors; import javax.annotation.Nullable; @@ -231,8 +231,11 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage } @Override - public ImmutableList getClassFiles() throws IOException { - return new DirectoryWalker(Paths.get(project.getBuild().getOutputDirectory())).walk().asList(); + public List getClassFiles() throws IOException { + return new DirectoryWalker(Paths.get(project.getBuild().getOutputDirectory())) + .filter(path -> path.getFileName().endsWith(".class")) + .walk() + .asList(); } @Override diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java index 52f9cb25d3..05857b37b0 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java @@ -19,9 +19,9 @@ import com.google.cloud.tools.jib.api.JibContainerBuilder; import com.google.cloud.tools.jib.api.RegistryImage; import com.google.cloud.tools.jib.event.EventHandlers; -import com.google.common.collect.ImmutableList; import java.io.IOException; import java.nio.file.Path; +import java.util.List; import javax.annotation.Nullable; /** Project property methods that require maven/gradle-specific implementations. */ @@ -48,7 +48,7 @@ public interface ProjectProperties { JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) throws IOException; - ImmutableList getClassFiles() throws IOException; + List getClassFiles() throws IOException; Path getDefaultCacheDirectory(); From 107535147e8a585845accbdcd9468e2130b5832d Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Mon, 25 Mar 2019 17:20:45 -0400 Subject: [PATCH 18/20] Feedback --- .../tools/jib/api/JavaContainerBuilder.java | 38 +------------------ .../jib/gradle/GradleProjectProperties.java | 5 +-- .../gradle/GradleProjectPropertiesTest.java | 11 +++--- .../jib/maven/MavenProjectProperties.java | 2 +- .../jib/maven/MavenProjectPropertiesTest.java | 12 +++--- .../common/JavaContainerBuilderHelper.java | 8 ++-- .../JavaContainerBuilderHelperTest.java | 10 ++--- 7 files changed, 26 insertions(+), 60 deletions(-) diff --git a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java index fd30d1f6e1..fc01bbb07f 100644 --- a/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java +++ b/jib-core/src/main/java/com/google/cloud/tools/jib/api/JavaContainerBuilder.java @@ -18,7 +18,6 @@ import com.google.cloud.tools.jib.ProjectInfo; import com.google.cloud.tools.jib.filesystem.AbsoluteUnixPath; -import com.google.cloud.tools.jib.filesystem.DirectoryWalker; import com.google.cloud.tools.jib.filesystem.RelativeUnixPath; import com.google.cloud.tools.jib.frontend.JavaEntrypointConstructor; import com.google.cloud.tools.jib.frontend.JavaLayerConfigurations; @@ -33,7 +32,6 @@ import java.nio.file.Path; import java.util.ArrayList; import java.util.Arrays; -import java.util.Collections; import java.util.LinkedHashSet; import java.util.List; import java.util.Map.Entry; @@ -229,8 +227,8 @@ public JavaContainerBuilder addDependencies(List dependencyFiles) throws I if (!Files.exists(file)) { throw new NoSuchFileException(file.toString()); } - addedDependencies.add(file); } + addedDependencies.addAll(dependencyFiles); classpathOrder.add(LayerType.DEPENDENCIES); return this; } @@ -247,40 +245,6 @@ public JavaContainerBuilder addDependencies(Path... dependencyFiles) throws IOEx return addDependencies(Arrays.asList(dependencyFiles)); } - /** - * Adds the contents of a dependency JAR directory to the image. Duplicate JAR filenames are - * renamed with the filesize in order to avoid collisions. - * - * @param dependenciesDirectory the directory containing dependency JARs to add to the image - * @return this - * @throws IOException if adding the layer fails - */ - public JavaContainerBuilder addDependencies(Path dependenciesDirectory) throws IOException { - if (!Files.isDirectory(dependenciesDirectory)) { - return addDependencies(Collections.singletonList(dependenciesDirectory)); - } - return addDependencies(dependenciesDirectory, path -> true); - } - - /** - * Adds the contents of a dependency JAR directory to the image. Duplicate JAR filenames are - * renamed with the filesize in order to avoid collisions. - * - * @param dependenciesDirectory the directory containing dependency JARs to add to the image - * @param pathFilter filter that determines which files (not directories) should be added - * @return this - * @throws IOException if adding the layer fails - */ - public JavaContainerBuilder addDependencies( - Path dependenciesDirectory, Predicate pathFilter) throws IOException { - return addDependencies( - new DirectoryWalker(dependenciesDirectory) - .filterRoot() - .filter(pathFilter) - .filter(path -> !Files.isDirectory(path)) - .walk() - .asList()); - } /** * Adds the contents of a resources directory to the image. * diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index 16d8e46949..cb903c1a7d 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -34,7 +34,6 @@ import com.google.cloud.tools.jib.plugins.common.logging.ProgressDisplayGenerator; import com.google.cloud.tools.jib.plugins.common.logging.SingleThreadedExecutor; import com.google.common.annotations.VisibleForTesting; -import com.google.common.collect.ImmutableList; import java.io.File; import java.io.IOException; import java.nio.file.Files; @@ -216,7 +215,7 @@ public List getClassFiles() throws IOException { SourceSet mainSourceSet = javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); FileCollection classesOutputDirectories = mainSourceSet.getOutput().getClassesDirs().filter(File::exists); - ImmutableList.Builder classFiles = ImmutableList.builder(); + List classFiles = new ArrayList<>(); for (File classesOutputDirectory : classesOutputDirectories) { classFiles.addAll( new DirectoryWalker(classesOutputDirectory.toPath()) @@ -224,7 +223,7 @@ public List getClassFiles() throws IOException { .walk() .asList()); } - return classFiles.build(); + return classFiles; } @Override diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index 15295b8c4e..c35789702a 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -117,16 +117,17 @@ private static class ContainerBuilderLayers { private ContainerBuilderLayers(BuildConfiguration configuration) { resourcesLayerEntries = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); - classesLayerEntries = getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + getLayerConfigurationsByName(configuration, LayerType.RESOURCES.getName()); + classesLayerEntries = + getLayerConfigurationsByName(configuration, LayerType.CLASSES.getName()); dependenciesLayerEntries = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.DEPENDENCIES.getName()); snapshotsLayerEntries = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); } } - private static List getLayerConfigurationByName( + private static List getLayerConfigurationsByName( BuildConfiguration buildConfiguration, String name) { return buildConfiguration .getLayerConfigurations() diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index 979127cbf4..19c53e73e9 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -198,7 +198,7 @@ static int getVersionFromString(String versionString) { public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) throws IOException { try { - if (MojoCommon.isWarProject(project)) { + if (isWarProject()) { Path explodedWarPath = Paths.get(project.getBuild().getDirectory()).resolve(project.getBuild().getFinalName()); return JavaContainerBuilderHelper.fromExplodedWar(baseImage, explodedWarPath, appRoot); diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index f68f9b9683..2c1ef09409 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -72,16 +72,18 @@ private static class ContainerBuilderLayers { private final List snapshotsLayerEntries; private ContainerBuilderLayers(BuildConfiguration configuration) { - resourcesLayerEntries = getLayerEntriesByName(configuration, LayerType.RESOURCES.getName()); - classesLayerEntries = getLayerEntriesByName(configuration, LayerType.CLASSES.getName()); + resourcesLayerEntries = + getLayerConfigurationsByName(configuration, LayerType.RESOURCES.getName()); + classesLayerEntries = + getLayerConfigurationsByName(configuration, LayerType.CLASSES.getName()); dependenciesLayerEntries = - getLayerEntriesByName(configuration, LayerType.DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.DEPENDENCIES.getName()); snapshotsLayerEntries = - getLayerEntriesByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); } } - private static List getLayerEntriesByName( + private static List getLayerConfigurationsByName( BuildConfiguration buildConfiguration, String name) { return buildConfiguration .getLayerConfigurations() diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java index 3c9a7d9bfc..78cd174e43 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelper.java @@ -50,11 +50,11 @@ public static LayerConfiguration extraDirectoryLayerConfiguration( new DirectoryWalker(extraDirectory) .filterRoot() .walk( - path -> { + localPath -> { AbsoluteUnixPath pathOnContainer = - AbsoluteUnixPath.get("/").resolve(extraDirectory.relativize(path)); + AbsoluteUnixPath.get("/").resolve(extraDirectory.relativize(localPath)); builder.addEntry( - path, pathOnContainer, extraDirectoryPermissions.get(pathOnContainer)); + localPath, pathOnContainer, extraDirectoryPermissions.get(pathOnContainer)); }); return builder.build(); } @@ -91,7 +91,7 @@ public static JibContainerBuilder fromExplodedWar( javaContainerBuilder.addClasses(webInfClasses, isClassFile); } if (Files.exists(webInfLib)) { - javaContainerBuilder.addDependencies(webInfLib); + javaContainerBuilder.addDependencies(new DirectoryWalker(webInfLib).filterRoot().walk()); } return javaContainerBuilder.toContainerBuilder(); } diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java index 826629120d..f6c3ef3348 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/JavaContainerBuilderHelperTest.java @@ -65,7 +65,7 @@ private static void assertExtractionPathsUnordered( expectedPaths, entries, layerEntry -> layerEntry.getExtractionPath().toString()); } - private static List getLayerConfigurationByName( + private static List getLayerConfigurationsByName( BuildConfiguration buildConfiguration, String name) { return buildConfiguration .getLayerConfigurations() @@ -114,13 +114,13 @@ public void testFromExplodedWar() MoreExecutors.newDirectExecutorService()); List resourcesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.RESOURCES.getName()); + getLayerConfigurationsByName(configuration, LayerType.RESOURCES.getName()); List classesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.CLASSES.getName()); + getLayerConfigurationsByName(configuration, LayerType.CLASSES.getName()); List dependenciesLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.DEPENDENCIES.getName()); List snapshotsLayerConfigurations = - getLayerConfigurationByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); + getLayerConfigurationsByName(configuration, LayerType.SNAPSHOT_DEPENDENCIES.getName()); assertSourcePathsUnordered( Collections.singletonList(temporaryExplodedWar.resolve("WEB-INF/lib/dependency-1.0.0.jar")), From 1d007f70823355efa0cc24b176430a7722b98921 Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Mon, 25 Mar 2019 17:32:37 -0400 Subject: [PATCH 19/20] Fix --- .../cloud/tools/jib/gradle/GradleProjectProperties.java | 6 +----- .../cloud/tools/jib/maven/MavenProjectProperties.java | 5 +---- 2 files changed, 2 insertions(+), 9 deletions(-) diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index cb903c1a7d..614c1cb2b8 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -217,11 +217,7 @@ public List getClassFiles() throws IOException { mainSourceSet.getOutput().getClassesDirs().filter(File::exists); List classFiles = new ArrayList<>(); for (File classesOutputDirectory : classesOutputDirectories) { - classFiles.addAll( - new DirectoryWalker(classesOutputDirectory.toPath()) - .filter(path -> path.getFileName().endsWith(".class")) - .walk() - .asList()); + classFiles.addAll(new DirectoryWalker(classesOutputDirectory.toPath()).walk().asList()); } return classFiles; } diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index 19c53e73e9..0c850e3105 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -232,10 +232,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage @Override public List getClassFiles() throws IOException { - return new DirectoryWalker(Paths.get(project.getBuild().getOutputDirectory())) - .filter(path -> path.getFileName().endsWith(".class")) - .walk() - .asList(); + return new DirectoryWalker(Paths.get(project.getBuild().getOutputDirectory())).walk().asList(); } @Override From 08475165ea5dec2453c07b672dc857a34471eb7f Mon Sep 17 00:00:00 2001 From: "tad.cordle@gmail.com" Date: Wed, 27 Mar 2019 10:29:03 -0400 Subject: [PATCH 20/20] Naming --- .../jib/gradle/GradleProjectProperties.java | 4 ++-- .../gradle/GradleProjectPropertiesTest.java | 23 +++++++++---------- .../jib/maven/MavenProjectProperties.java | 3 +-- .../jib/maven/MavenProjectPropertiesTest.java | 16 ++++++------- .../common/PluginConfigurationProcessor.java | 2 +- .../jib/plugins/common/ProjectProperties.java | 9 +++++++- .../PluginConfigurationProcessorTest.java | 2 +- 7 files changed, 32 insertions(+), 27 deletions(-) diff --git a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java index 614c1cb2b8..141dba3839 100644 --- a/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java +++ b/jib-gradle-plugin/src/main/java/com/google/cloud/tools/jib/gradle/GradleProjectProperties.java @@ -153,7 +153,7 @@ private static boolean isProgressFooterEnabled(Project project) { } @Override - public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) { + public JibContainerBuilder createContainerBuilder(RegistryImage baseImage) { try { if (isWarProject()) { logger.info("WAR project identified, creating WAR image: " + project.getDisplayName()); @@ -209,7 +209,7 @@ public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage @Override public List getClassFiles() throws IOException { - // TODO: Consolidate with getContainerBuilderWithLayers + // TODO: Consolidate with createContainerBuilder JavaPluginConvention javaPluginConvention = project.getConvention().getPlugin(JavaPluginConvention.class); SourceSet mainSourceSet = javaPluginConvention.getSourceSets().getByName(MAIN_SOURCE_SET_NAME); diff --git a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java index c35789702a..da4a7cbf3f 100644 --- a/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java +++ b/jib-gradle-plugin/src/test/java/com/google/cloud/tools/jib/gradle/GradleProjectPropertiesTest.java @@ -321,7 +321,7 @@ public void testGetMajorJavaVersion_jvm11() { } @Test - public void testGetContainerBuilderWithLayers_correctFiles() + public void testCreateContainerBuilder_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration("/app"); @@ -355,17 +355,16 @@ public void testGetContainerBuilderWithLayers_correctFiles() } @Test - public void testGetContainerBuilderWithLayers_noClassesFiles() - throws InvalidImageReferenceException { + public void testCreateContainerBuilder_noClassesFiles() throws InvalidImageReferenceException { Path nonexistentFile = Paths.get("/nonexistent/file"); Mockito.when(mockMainSourceSetOutput.getClassesDirs()) .thenReturn(new TestFileCollection(ImmutableSet.of(nonexistentFile))); - gradleProjectProperties.getContainerBuilderWithLayers(RegistryImage.named("base")); + gradleProjectProperties.createContainerBuilder(RegistryImage.named("base")); Mockito.verify(mockLogger).warn("No classes files were found - did you compile your project?"); } @Test - public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() + public void testCreateContainerBuilder_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration("/my/app"); ContainerBuilderLayers layers = new ContainerBuilderLayers(configuration); @@ -394,7 +393,7 @@ public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() } @Test - public void testGetContainerBuilderWithLayers_defaultAppRoot() + public void testCreateContainerBuilder_defaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(JavaLayerConfigurations.DEFAULT_APP_ROOT); @@ -421,7 +420,7 @@ public void testGetContainerBuilderWithLayers_defaultAppRoot() } @Test - public void testGetContainerBuilderWithLayers_war() + public void testCreateContainerBuilder_war() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { Path webAppDirectory = getResource("gradle/webapp"); @@ -487,7 +486,7 @@ public void testGetContainerBuilderWithLayers_war() } @Test - public void testGetContainerBuilderWithLayers_defaultWebAppRoot() + public void testCreateContainerBuilder_defaultWebAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { setUpWarProject(getResource("gradle/webapp")); @@ -524,7 +523,7 @@ public void testGetContainerBuilderWithLayers_defaultWebAppRoot() } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfClassesDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "lib"); setUpWarProject(temporaryFolder.getRoot().toPath()); @@ -532,7 +531,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfLibDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war", "WEB-INF", "classes"); setUpWarProject(temporaryFolder.getRoot().toPath()); @@ -540,7 +539,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("jib-exploded-war"); setUpWarProject(temporaryFolder.getRoot().toPath()); @@ -550,7 +549,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() private BuildConfiguration setupBuildConfiguration(String appRoot) throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { return new GradleProjectProperties(mockProject, mockLogger, AbsoluteUnixPath.get(appRoot)) - .getContainerBuilderWithLayers(RegistryImage.named("base")) + .createContainerBuilder(RegistryImage.named("base")) .toBuildConfiguration( Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); } diff --git a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java index 0c850e3105..ad34a38c44 100644 --- a/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java +++ b/jib-maven-plugin/src/main/java/com/google/cloud/tools/jib/maven/MavenProjectProperties.java @@ -195,8 +195,7 @@ static int getVersionFromString(String versionString) { } @Override - public JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) - throws IOException { + public JibContainerBuilder createContainerBuilder(RegistryImage baseImage) throws IOException { try { if (isWarProject()) { Path explodedWarPath = diff --git a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java index 2c1ef09409..80d56dae49 100644 --- a/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java +++ b/jib-maven-plugin/src/test/java/com/google/cloud/tools/jib/maven/MavenProjectPropertiesTest.java @@ -358,7 +358,7 @@ public void isProgressFooterEnabled() { } @Test - public void testGetContainerBuilderWithLayers_correctFiles() + public void testCreateContainerBuilder_correctFiles() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/app")); @@ -399,14 +399,14 @@ public void testGetContainerBuilderWithLayers_correctFiles() } @Test - public void testGetContainerBuilderWithLayers_nonDefaultAppRoot() + public void testCreateContainerBuilder_nonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { BuildConfiguration configuration = setupBuildConfiguration(AbsoluteUnixPath.get("/my/app")); assertNonDefaultAppRoot(configuration); } @Test - public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() + public void testCreateContainerBuilder_warNonDefaultAppRoot() throws URISyntaxException, IOException, InvalidImageReferenceException, CacheDirectoryCreationException { Path outputPath = getResource("maven/webapp"); @@ -473,7 +473,7 @@ public void testGetContainerBuilderWithLayers_warNonDefaultAppRoot() } @Test - public void testGetContainerBuilderWithLayers_jarNonDefaultAppRoot() + public void testCreateContainerBuilder_jarNonDefaultAppRoot() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { // Test when the default packaging is set Mockito.when(mockMavenProject.getPackaging()).thenReturn("jar"); @@ -482,7 +482,7 @@ public void testGetContainerBuilderWithLayers_jarNonDefaultAppRoot() } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); @@ -494,7 +494,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfDoesNotExist() } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfLibDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "classes"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); @@ -506,7 +506,7 @@ public void testGetContainerBuilderWithLayers_noErrorIfWebInfLibDoesNotExist() } @Test - public void testGetContainerBuilderWithLayers_noErrorIfWebInfClassesDoesNotExist() + public void testCreateContainerBuilder_noErrorIfWebInfClassesDoesNotExist() throws IOException, InvalidImageReferenceException, CacheDirectoryCreationException { temporaryFolder.newFolder("final-name", "WEB-INF", "lib"); Mockito.when(mockMavenProject.getPackaging()).thenReturn("war"); @@ -544,7 +544,7 @@ public void testIsWarProject_GwtLibPackagingIsNotWar() { private BuildConfiguration setupBuildConfiguration(AbsoluteUnixPath appRoot) throws InvalidImageReferenceException, IOException, CacheDirectoryCreationException { return new MavenProjectProperties(mockMavenProject, mockMavenSession, mockLog, appRoot) - .getContainerBuilderWithLayers(RegistryImage.named("base")) + .createContainerBuilder(RegistryImage.named("base")) .toBuildConfiguration( Containerizer.to(RegistryImage.named("to")), MoreExecutors.newDirectExecutorService()); } diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java index 2c9e997995..2b33a86559 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessor.java @@ -188,7 +188,7 @@ static PluginConfigurationProcessor processCommonConfiguration( JibContainerBuilder jibContainerBuilder = projectProperties - .getContainerBuilderWithLayers(baseImage) + .createContainerBuilder(baseImage) .setEntrypoint(computeEntrypoint(rawConfiguration, projectProperties)) .setProgramArguments(rawConfiguration.getProgramArguments().orElse(null)) .setEnvironment(rawConfiguration.getEnvironment()) diff --git a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java index 05857b37b0..e9716ddb6c 100644 --- a/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java +++ b/jib-plugins-common/src/main/java/com/google/cloud/tools/jib/plugins/common/ProjectProperties.java @@ -46,7 +46,14 @@ public interface ProjectProperties { String getPluginName(); - JibContainerBuilder getContainerBuilderWithLayers(RegistryImage baseImage) throws IOException; + /** + * Starts the containerization process. + * + * @param baseImage the base image + * @return a {@link JibContainerBuilder} with classes, resources, and dependencies added to it + * @throws IOException if there is a problem walking the project files + */ + JibContainerBuilder createContainerBuilder(RegistryImage baseImage) throws IOException; List getClassFiles() throws IOException; diff --git a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java index de1f4af95f..af0c098d55 100644 --- a/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java +++ b/jib-plugins-common/src/test/java/com/google/cloud/tools/jib/plugins/common/PluginConfigurationProcessorTest.java @@ -102,7 +102,7 @@ public void setUp() throws IOException, InvalidImageReferenceException { Mockito.when(projectProperties.getEventHandlers()) .thenReturn(new EventHandlers().add(JibEventType.LOGGING, logger)); Mockito.when(projectProperties.getDefaultCacheDirectory()).thenReturn(Paths.get("cache")); - Mockito.when(projectProperties.getContainerBuilderWithLayers(Mockito.any())) + Mockito.when(projectProperties.createContainerBuilder(Mockito.any())) .thenReturn( Jib.from("base") .setLayers(JavaLayerConfigurations.builder().build().getLayerConfigurations()));