Skip to content

Commit

Permalink
Initial commit for a 'docker:source' goal.
Browse files Browse the repository at this point in the history
Implements #311
  • Loading branch information
rhuss committed Oct 26, 2015
1 parent 08863ff commit 5a7bea8
Show file tree
Hide file tree
Showing 12 changed files with 205 additions and 20 deletions.
3 changes: 3 additions & 0 deletions doc/changelog.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
# ChangeLog

* **0.13.7-SNAPSHOT**
- New goal 'docker:source' for attaching a Docker tar archive to the Maven project with an classifier "docker-<alias>" (#311)

* **0.13.6**
- Don't use user from image when pulling base images ([#147](https://github.com/rhuss/docker-maven-plugin/issues/147))
- Add a new assembly descriptor reference `hawt-app` for using asseblies created by
Expand Down
1 change: 1 addition & 0 deletions doc/manual/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,5 @@ This is a Maven plugin for managing Docker images and containers for your builds
| [`docker:push`](docker-push.md) | Push images to a registry |
| [`docker:remove`](docker-remove.md) | Remove images from local docker host |
| [`docker:logs`](docker-logs.md) | Show container logs |
| [`docker:logs`](docker-source.md) | Attach docker build archive to Maven project |

1 change: 1 addition & 0 deletions doc/manual/SUMMARY.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
- [docker:push](docker-push.md)
- [docker:remove](docker-remove.md)
- [docker:logs](docker-logs.md)
- [docker:source](docker-source.md)
* [External Configuration](external-configuration.md)
* [Registry Handling](registry-handling.md)
* [Authentication](authentication.md)
Expand Down
3 changes: 3 additions & 0 deletions doc/manual/docker-build.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,9 @@ of an image configuration. The available subelements are
Dockerfile. This tag is not to be confused with the `<run>` section for this image which specifies the runtime
behaviour when starting containers.
* **optimise** if set to true then it will compress all the `runCmds` into a single RUN directive so that only one image layer is created.
* **compression** is the compression mode how the build archive is transmitted to the docker daemon (`docker:build`) and how
docker build archives are attached to this build as sources (`docker:source`). The value can be `none` (default),
`gzip` or `bzip2`.
* **skip** if set to true disables building of the image. This config option is best used together with a maven property
* **tags** contains a list of additional `tag` elements with which an
image is to be tagged after the build.
Expand Down
34 changes: 34 additions & 0 deletions doc/manual/docker-source.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
### docker:source

The `docker:source` target can be used to attach a docker build
archive containing the Dockerfile and all added files to the Maven
project with a certain classifier. It reuses the configuration from
[docker:build](docker-build.md).

`docker:source` uses the image's [alias](image-configuration.md) as
part of the classifier, so it is mandatory that the alias is set for
this goal to work. The classifier is calculated as `docker-<alias>` so
when the alias is set to `service`, then the classifier is
`docker-service`.

`docker:source` can be attached to a Maven execution phase, which is
`generate-sources` by default.

For example, this configuration will attach the docker build archive
to the artifacts to store in the repository:

````xml
<plugin>
<artifactId>docker-maven-plugin</artifactId>
<!-- ..... -->
<executions>
<execution>
<id>sources</id>
<goals>
<goal>source</goal>
</goals>
</execution>
</executions>
</plugin>
````

17 changes: 9 additions & 8 deletions doc/manual/goals.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,15 @@
This plugin supports the following goals which are explained in detail
in the following sections.

| Goal | Description |
| -------------------------------- | ------------------------------------ |
| [`docker:build`](dockerbuild.md) | Build images |
| [`docker:start`](dockerstart.md) | Create and start containers |
| [`docker:stop`](dockerstop.md) | Stop and destroy containers |
| [`docker:push`](dockerpush.md) | Push images to a registry |
| [`docker:remove`](dockerremove.md) | Remove images from local docker host |
| [`docker:logs`](dockerlogs.md) | Show container logs |
| Goal | Description |
| ----------------------------------- | ------------------------------------ |
| [`docker:build`](docker-build.md) | Build images |
| [`docker:start`](docker-start.md) | Create and start containers |
| [`docker:stop`](docker-stop.md) | Stop and destroy containers |
| [`docker:push`](docker-push.md) | Push images to a registry |
| [`docker:remove`](docker-remove.md) | Remove images from local docker host |
| [`docker:logs`](docker-logs.md) | Show container logs |
| [`docker:source`](docker-source.md) | Attach docker build archive to Maven project |

Note that all goals are orthogonal to each other. For example in order
to start a container for your application you typically have to build
Expand Down
8 changes: 7 additions & 1 deletion samples/data-jolokia-demo/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@

<groupId>org.jolokia</groupId>
<artifactId>docker-jolokia-demo</artifactId>
<version>0.13.6</version>
<version>0.13.7-SNAPSHOT</version>

<url>http://www.jolokia.org</url>

Expand Down Expand Up @@ -171,6 +171,12 @@
<goal>stop</goal>
</goals>
</execution>
<execution>
<id>sources</id>
<goals>
<goal>source</goal>
</goals>
</execution>
</executions>
</plugin>

Expand Down
65 changes: 65 additions & 0 deletions src/main/java/org/jolokia/docker/maven/SourceMojo.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
package org.jolokia.docker.maven;/*
*
* Copyright 2015 Roland Huss
*
* 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.
*/

import java.io.File;

import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.project.MavenProjectHelper;
import org.jolokia.docker.maven.access.DockerAccess;
import org.jolokia.docker.maven.access.DockerAccessException;
import org.jolokia.docker.maven.config.BuildImageConfiguration;
import org.jolokia.docker.maven.config.ImageConfiguration;
import org.jolokia.docker.maven.util.MojoParameters;

/**
* Mojo for attaching one more source docker tar file to an artifact.
*
* @goal source
* @phase package
* @execute phase="generate-sources"
* @executionStrategy once-per-session
*
* @author roland
* @since 25/10/15
*/
public class SourceMojo extends AbstractBuildSupportMojo {

/** @component */
private MavenProjectHelper projectHelper;

@Override
protected void executeInternal(DockerAccess dockerAccess) throws DockerAccessException, MojoExecutionException {
MojoParameters params = createMojoParameters();
for (ImageConfiguration imageConfig : getImages()) {
BuildImageConfiguration buildConfig = imageConfig.getBuildConfiguration();
if (buildConfig != null) {
if (buildConfig.skip()) {
log.info(imageConfig.getDescription() + ": Skipped creating source");
} else {
File dockerTar = serviceHub.getBuildService().createDockerBuildTar(imageConfig, params);
String alias = imageConfig.getAlias();
if (alias == null) {
throw new IllegalArgumentException(
"Image " + imageConfig.getDescription() + " must have an 'alias' configured to be " +
"used as a classifier for attaching a docker build tar as source to the maven build");
}
projectHelper.attachArtifact(project, buildConfig.getCompression().getFileSuffix(),"docker-" + alias, dockerTar);
}
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
import org.apache.maven.plugin.assembly.model.Assembly;
import org.apache.maven.shared.utils.PathTool;
import org.apache.maven.shared.utils.io.FileUtils;
import org.apache.maven.wagon.PathUtils;
import org.codehaus.plexus.archiver.Archiver;
import org.codehaus.plexus.archiver.manager.ArchiverManager;
import org.codehaus.plexus.archiver.manager.NoSuchArchiverException;
Expand Down Expand Up @@ -87,7 +86,7 @@ public File createDockerTarArchive(String imageName, MojoParameters params, Buil
builder.write(buildDirs.getOutputDirectory());
}

return createBuildTarBall(buildDirs, extraDir, assemblyMode);
return createBuildTarBall(buildDirs, extraDir, assemblyMode, buildConfig.getCompression());

} catch (IOException e) {
throw new MojoExecutionException(String.format("Cannot create Dockerfile in %s", buildDirs.getOutputDirectory()), e);
Expand Down Expand Up @@ -164,8 +163,8 @@ private File prepareChangedFilesArchivePath(File archiveDir, File destFile, File
return new File(archiveDir,relativePath);
}

private File createBuildTarBall(BuildDirs buildDirs, File extraDir, AssemblyMode buildMode) throws MojoExecutionException {
File archive = new File(buildDirs.getTemporaryRootDirectory(), "docker-build.tar");
private File createBuildTarBall(BuildDirs buildDirs, File extraDir, AssemblyMode buildMode, BuildTarArchiveCompression compression) throws MojoExecutionException {
File archive = new File(buildDirs.getTemporaryRootDirectory(), "docker-build." + compression.getFileSuffix());
try {
TarArchiver archiver = createBuildArchiver(buildDirs.getOutputDirectory(), archive, buildMode);
if (extraDir != null) {
Expand All @@ -176,6 +175,7 @@ private File createBuildTarBall(BuildDirs buildDirs, File extraDir, AssemblyMode
archiver.addFile(new File(buildDirs.getOutputDirectory(),"Dockerfile"), "Dockerfile");
}
archiver.createArchive();
archiver.setCompression(compression.getTarCompressionMethod());
return archive;
} catch (NoSuchArchiverException e) {
throw new MojoExecutionException("No archiver for type 'tar' found", e);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import java.util.*;

import org.codehaus.plexus.archiver.tar.TarArchiver;
import org.jolokia.docker.maven.util.Logger;

/**
Expand Down Expand Up @@ -97,7 +98,12 @@ public class BuildImageConfiguration {
* @parameter
*/
private boolean skip = false;


/**
* @parameter
*/
private BuildTarArchiveCompression compression = BuildTarArchiveCompression.none;

public BuildImageConfiguration() {}

public String getFrom() {
Expand Down Expand Up @@ -144,7 +150,6 @@ public Arguments getCmd() {
return cmd;
}


@Deprecated
public String getCommand() {
return command;
Expand All @@ -162,6 +167,10 @@ public boolean skip() {
return skip;
}

public BuildTarArchiveCompression getCompression() {
return compression;
}

public Arguments getEntryPoint() {
return entryPoint;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package org.jolokia.docker.maven.config;/*
*
* Copyright 2015 Roland Huss
*
* 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.
*/

import org.codehaus.plexus.archiver.tar.TarArchiver;

/**
* Enumeration for determine the compression mode when creating docker
* build archives.
*
* @author roland
* @since 26/10/15
*/
public enum BuildTarArchiveCompression {

none(TarArchiver.TarCompressionMethod.none, "tar"),
gzip(TarArchiver.TarCompressionMethod.gzip,"tar.gz"),
bzip2(TarArchiver.TarCompressionMethod.bzip2,"tar.bz");

private final TarArchiver.TarCompressionMethod tarCompressionMethod;
private final String fileSuffix;

BuildTarArchiveCompression(TarArchiver.TarCompressionMethod tarCompressionMethod, String fileSuffix) {
this.tarCompressionMethod = tarCompressionMethod;
this.fileSuffix = fileSuffix;
}

public TarArchiver.TarCompressionMethod getTarCompressionMethod() {
return tarCompressionMethod;
}

public String getFileSuffix() {
return fileSuffix;
}
}
24 changes: 19 additions & 5 deletions src/main/java/org/jolokia/docker/maven/service/BuildService.java
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,9 @@ public void buildImage(ImageConfiguration imageConfig, MojoParameters params)
oldImageId = queryService.getImageId(imageName);
}

File dockerArchive = createArchive(imageName, buildConfig, params);
// auto is now supported by docker, consider switching?
String newImageId = buildImage(imageName, buildConfig, params);
String newImageId = doBuildImage(imageName, dockerArchive, buildConfig.cleanup());
log.info(imageConfig.getDescription() + ": Built image " + newImageId);

if (oldImageShouldBeRemoved(oldImageId, newImageId)) {
Expand All @@ -61,6 +62,21 @@ public void buildImage(ImageConfiguration imageConfig, MojoParameters params)
}
}

/**
* Create the tar file container the source for building an image. This tar can be used directly for
* uploading to a Docker daemon for creating the image
*
* @param imageConfig the image configuration
* @param params mojo params for the project
* @return file for holding the sources
* @throws MojoExecutionException if during creation of the tar an error occurs.
*/
public File createDockerBuildTar(ImageConfiguration imageConfig, MojoParameters params) throws MojoExecutionException {
File ret = createArchive(imageConfig.getName(), imageConfig.getBuildConfiguration(), params);
log.info(imageConfig.getDescription() + ": Created docker source tar " + ret);
return ret;
}

/**
* Get a mapping of original to destination files which a covered by an assembly. This can be used
* to watch the source files for changes in order to update the target (either by recreating a docker image
Expand Down Expand Up @@ -96,11 +112,9 @@ public File createChangedFilesArchive(List<AssemblyFiles.Entry> entries, File as

// ===============================================================

private String buildImage(String imageName, BuildImageConfiguration buildConfig, MojoParameters mojoParameters)
private String doBuildImage(String imageName, File dockerArchive, boolean cleanUp)
throws DockerAccessException, MojoExecutionException {

File dockerArchive = createArchive(imageName, buildConfig, mojoParameters);
docker.buildImage(imageName, dockerArchive, buildConfig.cleanup());
docker.buildImage(imageName, dockerArchive, cleanUp);
return queryService.getImageId(imageName);
}

Expand Down

0 comments on commit 5a7bea8

Please sign in to comment.