001/* 002 * Copyright 2017-2022 original authors 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * https://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package io.micronaut.maven; 017 018import com.github.dockerjava.api.command.BuildImageCmd; 019import com.google.cloud.tools.jib.plugins.common.PropertyNames; 020import io.micronaut.maven.core.DockerBuildStrategy; 021import io.micronaut.maven.core.MicronautRuntime; 022import io.micronaut.maven.jib.JibConfigurationService; 023import io.micronaut.maven.services.ApplicationConfigurationService; 024import io.micronaut.maven.services.DockerService; 025import org.apache.maven.execution.MavenSession; 026import org.apache.maven.plugin.MojoExecution; 027import org.apache.maven.plugin.MojoExecutionException; 028import org.apache.maven.plugins.annotations.Mojo; 029import org.apache.maven.plugins.annotations.ResolutionScope; 030import org.apache.maven.project.MavenProject; 031 032import javax.inject.Inject; 033import java.io.File; 034import java.io.IOException; 035import java.nio.file.Files; 036import java.nio.file.LinkOption; 037import java.nio.file.StandardCopyOption; 038 039import static io.micronaut.maven.DockerfileMojo.DOCKERFILE_ORACLE_CLOUD; 040 041/** 042 * <p>Allows using a provided Dockerfile.</p> 043 * <p><strong>WARNING</strong>: this goal is not intended to be executed directly. Instead, specify the packaging type 044 * using the <code>packaging</code> property, eg:</p> 045 * 046 * <pre>mvn package -Dpackaging=docker</pre> 047 * 048 * @author Álvaro Sánchez-Mariscal 049 * @since 1.1 050 */ 051@Mojo(name = DockerMojo.DOCKER_PACKAGING, requiresDependencyResolution = ResolutionScope.COMPILE_PLUS_RUNTIME) 052public class DockerMojo extends AbstractDockerMojo { 053 054 public static final String DOCKER_PACKAGING = "docker"; 055 056 @SuppressWarnings("CdiInjectionPointsInspection") 057 @Inject 058 public DockerMojo(MavenProject mavenProject, JibConfigurationService jibConfigurationService, 059 ApplicationConfigurationService applicationConfigurationService, DockerService dockerService, 060 MavenSession mavenSession, MojoExecution mojoExecution) { 061 super(mavenProject, jibConfigurationService, applicationConfigurationService, dockerService, mavenSession, 062 mojoExecution); 063 } 064 065 @Override 066 public void execute() throws MojoExecutionException { 067 var providedDockerfile = new File(mavenProject.getBasedir(), DockerfileMojo.DOCKERFILE); 068 if (shouldBuildWithDockerfile(providedDockerfile)) { 069 var dockerfile = determineDockerfile(providedDockerfile); 070 buildDockerfile(dockerfile); 071 } else if (jibConfigurationService.getFromImage().isEmpty()) { 072 mavenProject.getProperties().setProperty(PropertyNames.FROM_IMAGE, getBaseImage()); 073 } 074 } 075 076 private File determineDockerfile(File providedDockerfile) throws MojoExecutionException { 077 if (providedDockerfile.exists()) { 078 return providedDockerfile; 079 } 080 try { 081 return dockerService.loadDockerfileAsResource(DOCKERFILE_ORACLE_CLOUD); 082 } catch (IOException e) { 083 throw new MojoExecutionException("Error loading Dockerfile", e); 084 } 085 } 086 087 private boolean shouldBuildWithDockerfile(File providedDockerfile) { 088 var runtime = MicronautRuntime.valueOf(micronautRuntime.toUpperCase()); 089 return providedDockerfile.exists() || runtime.getBuildStrategy() == DockerBuildStrategy.ORACLE_FUNCTION; 090 } 091 092 private void buildDockerfile(File dockerfile) throws MojoExecutionException { 093 try { 094 var runtime = MicronautRuntime.valueOf(micronautRuntime.toUpperCase()); 095 if (runtime.getBuildStrategy() == DockerBuildStrategy.ORACLE_FUNCTION) { 096 oracleCloudFunctionCmd(dockerfile); 097 DockerfileMojo.processOracleFunctionDockerfile(dockerfile); 098 } 099 getLog().info("Using Dockerfile: " + dockerfile.getAbsolutePath()); 100 mavenProject.getProperties().put(PropertyNames.SKIP, "true"); 101 102 copyDependencies(); 103 104 String targetDir = mavenProject.getBuild().getDirectory(); 105 var targetDockerfile = new File(targetDir, dockerfile.getName()); 106 Files.copy(dockerfile.toPath(), targetDockerfile.toPath(), LinkOption.NOFOLLOW_LINKS, 107 StandardCopyOption.REPLACE_EXISTING); 108 109 BuildImageCmd buildImageCmd = dockerService.buildImageCmd() 110 .withDockerfile(targetDockerfile) 111 .withTags(getTags()) 112 .withBaseDirectory(new File(targetDir)); 113 getNetworkMode().ifPresent(buildImageCmd::withNetworkMode); 114 dockerService.buildImage(buildImageCmd); 115 } catch (IOException e) { 116 throw new MojoExecutionException(e.getMessage(), e); 117 } 118 } 119 120}