Configure Spring Boot with Docker Secrets


You should have a reasonable well understanding of Docker before we continue here. Also you are not afraid of using a command line and have a basic understanding of Spring Boot, Maven or Java development in general.

The Problem

As consultants we’re quite often exposed to new code bases across various clients. And quite often, we find code like this in the very first repository we’re cloning:

Ok, this alone usually won’t allow me to go to the production DB and create havoc – in a serious setup this is also well hidden inside its own network zone which is normally not accessible by each and every developer. Still leaving production passwords in plain sight is simply wrong.

While there are various solutions around for this problem, here is one outlined which is very easy to integrate when working with Docker (who isn’t nowadays?). Docker introduced the swarm concept with version 1.12 (and in case you have not heard about swarm, you might definitely have a look at the documentation also to have the terminology for further reading), and with swarm in Docker 1.13 you can use Docker secrets. Yes, secrets currently can’t be used with “standalone” Docker – but if you run in a productive Docker environment without swarm, you really might want to consider it. Oh if you follow this blog further, there will actually be some hands on opportunity with swarm… Anyway, the main goal here is to show a convenient way on how to leverage Docker secrets with a Spring Boot microservice.

Docker secrets allow you to manage sensitive configuration values across a whole Docker cluster – Docker encrypts those values, distributes them in the swarm and allows you to grant your containers access to those values. Production passwords won’t have to show up ever again in your Git repo!

The drawback: Your Docker image has to support secrets. There are many developers already catching up with secrets (e.g. PostgreSQL or MySQL, see the “Docker Secrets” chapters for both) so you should not be limited to your own Docker images. Spring Boot might support this in the future natively, but for now I show you an alternative quick way to integrate this seamlessly into your microservice deployments.

Docker Swarm Setup

Action speaks louder than words! I have prepared a small demo where you can get your hands dirty. Please head over to our GitHub account and clone the demo repository. The demo is based on Vagrant and VirtualBox as it’s a simple way to create a multi-host Docker swarm without charging your credit card for a cloud provider. So after you’ve cloned the repo, spin up your favorite shell, cd into the cloned directory and run the demo environment with

This takes while as you probably first download the Vagrant base image and install a good bunch of software on it. Let’s quickly look at the Vagrantfile to see what we just got:

This results in:

  • A single node named swarm1 on IP (created in the # Swarm nodes section)
  • The node(s) have the latest Docker version installed, plus a JDK and Apache Maven. This is done in the shell scripts referenced in the vm.provision config.
  • The files in the stacks folder (docker-compose resp. Swarm stacks files) and the spring-boot directory (obviously our Spring Boot sources) have been copied over to the VM. See the vm.synced_folder entries for this.

From Single Node to Cluster

A single node swarm cluster? Yes, how boring! Feel free to add more nodes by just increasing the (1..1) to (1..x) – each node gets 2 GB of RAM, so make sure not to go over you machine’s limit. Also make sure to read the notes for multiple nodes in the post.

Credits to Wes Higbee for this swarm setup, you can find the base Vagrant setup I used on GitHub. He has also an excellent course on Docker swarm on Pluralsight.

We are using sdkman to install the JDK and Maven. If you read this in the far future and this breaks, it might be that the currently used JDK 8 disappeared from the options list. Please just update the provision/ file in this case.

Accessing the Box

Let’s login to the provisioned Vagrant box and start our Docker swarm:

If you have provisioned more nodes, log into those nodes and follow the instructions that just got printed out on the console. Swarm distinguishes between manager and worker nodes – some functionality will only be available on manager nodes, but a proper productive Swarm setup is beyond the scope of this post.

Let’s quickly visualize what’s going on in the swarm by jumping back into our Vagrant box. We’ll first deploy a so called stack to our swarm which is very simple using a compose file:

Pointing your browser to will show you an overview of your swarm (given the REPLICAS is really it 1/1, otherwise wait a little more until the container is started – image download first time might need a little time):

The Microservice

Let’s head over to our Spring Boot sources. We’re just exposing one REST endpoint:

We get a secret value injected and expose this over the REST endpoint. Yes, there are definitely smarter usages for secrets than just echoing it on a public REST service! In our local dev environment, the value comes out of the in our src/main/resources directory:

Spinning up the container for a test run is as simple as

and we get our REST endpoint content (in a new shell) with

The Secret

Let’s put our secret into the Docker swarm. We create a secret called “secret” (we injected this name in our Spring Boot code above) and put in the value “Docker Secrets!”. All that’s needed is a command like:

We can now authorize a swarm service to get access to this secret and exposing it under /run/secrets/[secret name] on the container file system. But how can we use this in our Spring Boot microservice in a transparent way (after all we don’t want custom code in our microservice to read this)?

Spring Boot supports reading an from the file system, which takes precedence over values defined in a classpath We can use this mechanism and simply have a shell script converting any available secrets to be written into a custom This is reflected in the src/main/docker/ script:

This adds a key-value pair in for each secret we received from swarm (secret name=secret value). We want to run this before our service so we need to combine this in a container entrypoint:

Combining all the parts into a Dockerfile looks like

Note that the CMD is passed as argument to the ENTRYPOINT. In order to use ENV variables, we have to run this over a sh shell command.

The Service

In order to put all the pieces together now, we have to create a Docker image of our microservice. We have a Dockerfile so let’s use our Maven build to create the image:

Docker Image: Check. Let’s deploy this as a service in our Docker swarm. Simply done (as before) with a compose file. We also grant the container(s) access to the secret:

As you see, we define the secret as external as we have already created it. Now we just spin up this stack executing

Did it work? Let’s see:

Service running: Check!

Secret picked up: Check!

Running on multiple nodes? Note that you created your image locally. In order to test this setup on multiple nodes, you need to publish the image to a registry (or build it on all other nodes, which is not very convenient). But then you can simply scale your service across multiple nodes with something like

You can watch the results on the visualizer.


This might look like a rather long description but overall we spent a good part setting up Swarm and our environment. This drills down to a simple modification on your Docker image, update the way you launch your service and add a secret to your swarm. Even better, the integration into the service workes transparently and does not impact your development process by adding a dependency on a specific technology.

Given this fits into your infrastructure this seems like a small price to pay to get rid of passwords in your version control system.

Stay up to date with our articles, job postings and events by subscribing to “Snapshot”, our monthly newsletter!

Tom Hug

Senior Technology Specialist at Atos Consulting
Tech nerd, OSS contributor and JVM aficionado. Coder at day, gamer at night. The rest of my time belongs to my family.

I have more than 15 years experience building distributed systems, and also know how to deploy and run them. Fluent in Java, and currently polishing again my language skills in Kotlin, C#, JavaScript and Python (in that order of preference).
Configure Spring Boot with Docker Secrets
Article Name
Configure Spring Boot with Docker Secrets
Learn how to keep your source repository free of production passwords using Docker Secrets and configure them with Spring Boot and Docker Swarm.
Publisher Name
Atos Consulting CH
Publisher Logo

5 thoughts on “Configure Spring Boot with Docker Secrets

  1. Avatar
    Hermann Steidel Reply

    I wish we didn’t have to jump through these hoops but very nice. Thank you. I was able to adopt this for use with Spring Cloud Config Client’s

  2. Avatar
    vaibhav goswami Reply

    docker stack deploy isnt respecting the extra_hosts parameter in my compose file. when i do a simple docker-compose up the entry is created in the /etc/hosts however when i do docker deploy –compose-file docker-compose.yml myapp it ignores extra_hosts, any insights?

  3. Pingback: Google Cloud Onboard Zurich - Atos Consulting CH

Leave a Reply

Your email address will not be published. Required fields are marked *