How to build and publish a Spring Boot app’s image using Dockerfile

Jean-Pascal MEWENEMESSE
4 min readMar 26, 2020

--

Containerization workflow

This post aims to be example-driven and you will learn to:

  1. Create a local repo using maven
  2. Create and Build a multi-stage Dockerfile and some commands descriptions
  3. Publish an image to DockerHub
  4. Run a container and access the application in a browser

If you don’t care about the “what, why, how” and just want the code examples, you can just skip this introduction.

Here is the complete Github project source code

Introduction

Before diving into images, let’s talk about what is a docker image. According to docker documentation

An image is an executable package that includes everything needed to run an application — the code or binary, runtimes, dependencies, and any other filesystem objects required

Lets put it simply, an image is a container that is not yet running and a container is a running instance of an image.

Docker images are created in different layers and the configuration file that builds that image is what is called a Dockerfile. According to documentation

A Dockerfile is a text document that contains all the commands a user could call on the command line to assemble an image

Installation prerequisites

To be able to run incoming scripts, you need to have Docker, JDK, Maven, and Git installed. You can test your installations by running in a bash terminal below commands. Your commands results might be similar to mine if you are using a Mac.

~ % docker --versionDocker version 19.03.8, build afacb8b~ % java -version
java version “1.8.0_241”
Java(TM) SE Runtime Environment (build 1.8.0_241-b07)Java HotSpot(TM) 64-Bit Server VM (build 25.241-b07, mixed mode)~ % mvn -versionApache Maven 3.6.3 (cecedd343002696d0abb50b32b541b8a6ba2883f)Maven home: /usr/local/Cellar/maven/3.6.3_1/libexecJava version: 1.8.0_241, vendor: Oracle Corporation, runtime: /Library/Java/JavaVirtualMachines/jdk1.8.0_241.jdk/Contents/Home/jreDefault locale: fr_FR, platform encoding: UTF-8OS name: "mac os x", version: "10.15.2", arch: "x86_64", family: "mac"~ % git --versiongit version 2.23.0

Run below command to have project source files locally. The project has been created using Spring Initilizr

~ % git clone https://github.com/pascalito007/samples.git
~ % cd samples

After cloning the project and before starting creating a Dockerfile, make sure to be in the project directory and type below two commands which create a local repository that will be copied later in the created image using Dockerfile.

  • mvn -Dmaven.repo.local=./repository clean package
  • tar cf repository.tar.gz ./repository

Create a Dockerfile

A multi-stage Dockerfile will be created and the complete file can be downloaded here.

Stage 1

FROM maven:3.6.3-jdk-8 as BUILD

The above instruction defines the base image of the Dockerfile. This first image layer will be called BUILD.

ADD repository.tar.gz /usr/share/maven/ref/

The above instruction will copy the local repository from the host machine to the image directory /usr/share/maven/ref/ which is available in maven image

COPY . /usr/src/app

The above instruction will copy all source code files to /usr/src/app

WORKDIR /usr/src/app

The above instruction will set the working directory

RUN mvn -s /usr/share/maven/ref/settings-docker.xml package

The above instruction will package the application

Stage 2

FROM openjdk:8-jre

The above instruction will define a new base image for the second stage

EXPOSE 8080

The above instruction will expose the container port that will be used later to bind to host port

COPY --from=BUILD /usr/src/app/target/*.jar /opt/target/app.jar

From BUILD layer in the first stage, copy the packaged jar file to /opt/target/ and rename it app.jar

WORKDIR /opt/target

The above instruction will set the new working directory

ENTRYPOINT ["java","-jar", "app.jar"]

The above instruction is the entry point when a running instance of the image will be created later on.

Create an image from previous Dockerfile

The image that will be created will be tagged 1.0 and YOUR_DOCKER_HUB_ID must be replaced with yours after creating a DockerHub account.

Open a bash terminal to run below command that will build the image.

docker build -t YOUR_DOCKER_HUB_ID/sample:1.0 .

View created image

Considering YOUR_DOCKER_HUB_ID is jdoe

samples % docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
jdoe/sample 1.0 53a2a53c0006 7 seconds ago 285MB

Run a container from the created image

To create a container that is a running instance of the image and expose the application port 8080 to the host on port 8080, run below command in a bash terminal. Your result might be similar to mine.

docker run -it -p 8080:8080 jdoe/sample:1.0
Running instance of the image and exposed to 8080 on the host

View created container

To view the running container, type below command in another terminal

docker ps
Created and running container

Access the application in a browser

The application can be accessed using http://localhost:8080

Access the running application in a browser

Publish the image to DockerHub

To be able to publish the image to a remote docker public registry, you first need to create an account at the Dockerhub website.

After your account created, open a bash terminal and run below command.

docker push YOUR_DOCKER_HUB_ID/sample:1.0

I hope you enjoyed and learned something from this article! If you did, follow me on Medium, or add me on LinkedIn for more articles about DevOps, Software Development, Angular and more!

--

--

Jean-Pascal MEWENEMESSE

I am a Software Engineer with Over 6 years working experiences, Oracle Certified Java EE Expert and Udacity Cloud DevOps Engineer Nanodegree Graduated…