Source: https://dzone.com/articles/spring-sweets-dockerize-spring-boot-application-wi
Spring Sweets: Dockerize Spring Boot Application With Jib
Creating Docker images for Java applications just became a lot easier. Let's take a look at how to use Jib to accomplish this goal quickly and easily with Jib.
by Hubert Klein Ikkink
Jib
is an open-source Java library from Google designed for creating Docker
images for Java applications. Jib can be used as a Maven or Gradle
plugin in our Spring Boot projects. One of the nice features of Jib is
that it adds layers to our classes, resources, and dependency libraries
for the Docker image. This means that when only class files have
changed, the classes layer is rebuilt, but the others remain the same.
Therefore, the creation of a Docker image with our Spring Boot
application is also very fast (after the first creation). Also, the
Maven and Gradle plugins have sensible defaults, like using the project
name and version as image name, so we don't have to configure anything
in our build tool. Although, Jib provides options to configure other
values for the defaults, for example, to change the JVM options passed
on to the application.
Let's see Jib in action in this sample Spring Boot
application. We will use Gradle as a build tool with the following
Spring Boot application:
// File: src/main/java/mrhaki/spring/sample/SampleApplication.java
package mrhaki.spring.sample;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import reactor.core.publisher.Mono;
public class SampleApplication {
public static void main(String[] args) {
SpringApplication.run(SampleApplication.class, args);
}
"/message") (
Mono<String> message() {
return Mono.just("Spring Boot sample application.");
}
}
Next, we add the Jib plugin to our Gradle build file:
// File: build.gradle
...
plugins {
id 'com.google.cloud.tools.jib' version '0.9.10'
}
...
With the Gradle task
jibDockerBuild
, we can create a Docker image for our local Docker. Our project is called springboot-sample
with version 1.0.0-SNAPSHOT
, so we get the Docker image springboot-sample:1.0.0-SNAPSHOT
:$ ./gradlew jibDockerBuild
Tagging image with generated image reference springboot-sample:1.0.0-SNAPSHOT. If you'd like to specify a different tag, you can set the jib.to.image parameter in your build.gradle, or use the --image=<MY IMAGE> commandline flag.
warning: Base image 'gcr.io/distroless/java' does not use a specific image digest - build may not be reproducible
Containerizing application to Docker daemon as springboot-sample:1.0.0-SNAPSHOT...
Getting base image gcr.io/distroless/java...
Building dependencies layer...
Building resources layer...
Building classes layer...
Finalizing...
Loading to Docker daemon...
Container entrypoint set to [java, -cp, /app/resources/:/app/classes/:/app/libs/*, mrhaki.spring.sample.SampleApplication]
Built image to Docker daemon as springboot-sample:1.0.0-SNAPSHOT
BUILD SUCCESSFUL in 3s
3 actionable tasks: 1 executed, 2 up-to-date
$
Notice that the default image our Docker image is built on
gcr.io/distroless/java
, but we can change that in our Gradle build file via the jib
configuration block.
Our image is available so we can run a Docker container based on our image and check the URL of our application:
$ docker run -d --name springboot-sample -p 8080:8080 springboot-sample:1.0.0-SNAPSHOT
5d288cbe4ed606760a51157734349135d4d4562072e1024f4585dff370ac6f99
$ curl -X GET http://localhost:8080/message
Spring Boot sample application.
$
In the following example, we can add some configuration for Jib in our Gradle build file:
// File: build.gradle
...
jib {
to {
image = "springboot-mrhaki:${project.version}"
}
container {
// Set JVM options.
jvmFlags = ['-XX:+UnlockExperimentalVMOptions', '-XX:+UseCGroupMemoryLimitForHeap', '-Dserver.port=9000']
// Expose different port.
ports = ['9000']
// Add labels.
labels = [maintainer: 'mrhaki']
}
}
...
When we run the
jibDockerBuild
task, a new Docker image is built:$ warning: Base image 'gcr.io/distroless/java' does not use a specific image digest - build may not be reproducible
Containerizing application to Docker daemon as springboot-mrhaki:1.0.0-SNAPSHOT...
Getting base image gcr.io/distroless/java...
Building dependencies layer...
Building resources layer...
Building classes layer...
Finalizing...
Loading to Docker daemon...
Container entrypoint set to [java, -XX:+UnlockExperimentalVMOptions, -XX:+UseCGroupMemoryLimitForHeap, -Dserver.port=9000, -cp, /app/resources/:/app/classes/:/app/libs/*, mrhaki.spring.sample.SampleApplication]
Built image to Docker daemon as springboot-mrhaki:1.0.0-SNAPSHOT
BUILD SUCCESSFUL in 3s
3 actionable tasks: 1 executed, 2 up-to-date
$ docker run -d --name springboot-mrhaki -p 9000:9000 springboot-mrhaki:1.0.0-SNAPSHOT
6966ff3b5ca8dae658d59e39c0f26c11d22af7e04e02ad423516572eb5e0e0bd
$ curl -X GET http://localhost:9000/message
Spring Boot sample application.
$
Jib also adds the
jib
task to deploy a Docker
image to a registry instead of the local Docker daemon. Jib can use
several command-line applications to authenticate registries, or we can
set authentication information in the Gradle build file. Check Jib on Github for more documentation of the options and features.
Written with Spring Boot 2.0.4.RELEASE and Jib Gradle plugin 0.9.10.