Reading properties from Spring Cloud Config Server

This guide explains how your Quarkus application can read configuration properties at runtime from the Spring Cloud Config Server.

Prerequisites

To complete this guide, you need:

  • Roughly 15 minutes

  • An IDE

  • JDK 11+ installed with JAVA_HOME configured appropriately

  • Apache Maven 3.8.1+

  • Optionally the Quarkus CLI if you want to use it

  • Optionally Mandrel or GraalVM installed and configured appropriately if you want to build a native executable (or Docker if you use a native container build)

Solution

We recommend that you follow the instructions in the next sections and create the application step by step.

Stand up a Config Server

To stand up the Config Server required for this guide, please follow the instructions outlined here. The end result of that process is a running Config Server that will provide the Hello world value for a configuration property named message when the application querying the server is named a-bootiful-client.

Creating the Maven project

First, we need a new project. Create a new project with the following command:

CLI
quarkus create app org.acme:spring-cloud-config-quickstart \
    --extension=resteasy-reactive,spring-cloud-config-client \
    --no-code
cd spring-cloud-config-quickstart

To create a Gradle project, add the --gradle or --gradle-kotlin-dsl option.

For more information about how to install the Quarkus CLI and use it, please refer to the Quarkus CLI guide.

Maven
mvn io.quarkus.platform:quarkus-maven-plugin:2.13.0.Final:create \
    -DprojectGroupId=org.acme \
    -DprojectArtifactId=spring-cloud-config-quickstart \
    -Dextensions="resteasy-reactive,spring-cloud-config-client" \
    -DnoCode
cd spring-cloud-config-quickstart

To create a Gradle project, add the -DbuildTool=gradle or -DbuildTool=gradle-kotlin-dsl option.

This command generates a project which imports the spring-cloud-config-client extension.

If you already have your Quarkus project configured, you can add the spring-cloud-config-client extension to your project by running the following command in your project base directory:

CLI
quarkus extension add 'spring-cloud-config-client'
Maven
./mvnw quarkus:add-extension -Dextensions="spring-cloud-config-client"
Gradle
./gradlew addExtension --extensions="spring-cloud-config-client"

This will add the following to your build file:

pom.xml
<dependency>
    <groupId>io.quarkus</groupId>
    <artifactId>quarkus-spring-cloud-config-client</artifactId>
</dependency>
build.gradle
implementation("io.quarkus:quarkus-spring-cloud-config-client")

GreetingController

First, create a simple GreetingResource JAX-RS resource in the src/main/java/org/acme/spring/cloud/config/client/GreetingResource.java file that looks like:

package org.acme.spring.spring.cloud.config.client;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

@Path("/hello")
public class GreetingResource {

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String hello() {
        return "hello";
    }
}

As we want to use configuration properties obtained from the Config Server, we will update the GreetingResource to inject the message property. The updated code will look like this:

package org.acme.spring.spring.cloud.config.client;

import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;

import org.eclipse.microprofile.config.inject.ConfigProperty;

@Path("/hello")
public class GreetingResource {

    @ConfigProperty(name = "message", defaultValue="hello default")
    String message;

    @GET
    @Produces(MediaType.TEXT_PLAIN)
    public String hello() {
        return message;
    }
}

Configuring the application

Quarkus provides various configuration knobs under the quarkus.spring-cloud-config root. For the purposes of this guide, our Quarkus application is going to be configured in application.properties as follows:

# use the same name as the application name that was configured when standing up the Config Server
quarkus.application.name=a-bootiful-client
# enable retrieval of configuration from the Config Server - this is off by default
quarkus.spring-cloud-config.enabled=true
# configure the URL where the Config Server listens to HTTP requests - this could have been left out since http://localhost:8888 is the default
quarkus.spring-cloud-config.url=http://localhost:8888

Package and run the application

Run the application with:

CLI
quarkus dev
Maven
./mvnw quarkus:dev
Gradle
./gradlew --console=plain quarkusDev

Open your browser to http://localhost:8080/greeting.

The result should be: Hello world as it is the value obtained from the Spring Cloud Config server.

Run the application as a native executable

You can of course create a native image using the instructions of the Building a native executable guide.

Spring Cloud Config Client Reference

Configuration property fixed at build time - All other configuration properties are overridable at runtime

Configuration property

Type

Default

If enabled, will try to read the configuration from a Spring Cloud Config Server

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_ENABLED

boolean

false

If set to true, the application will not stand up if it cannot obtain configuration from the Config Server

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_FAIL_FAST

boolean

false

The Base URI where the Spring Cloud Config Server is available

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_URL

string

http://localhost:8888

The label to be used to pull remote configuration properties. The default is set on the Spring Cloud Config Server (generally "master" when the server uses a Git backend).

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_LABEL

string

The amount of time to wait when initially establishing a connection before giving up and timing out. Specify 0 to wait indefinitely.

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_CONNECTION_TIMEOUT

Duration

10S

The amount of time to wait for a read on a socket before an exception is thrown. Specify 0 to wait indefinitely.

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_READ_TIMEOUT

Duration

60S

The username to be used if the Config Server has BASIC Auth enabled

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_USERNAME

string

The password to be used if the Config Server has BASIC Auth enabled

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_PASSWORD

string

TrustStore to be used containing the SSL certificate used by the Config server Can be either a classpath resource or a file system path

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_TRUST_STORE

path

Password of TrustStore to be used containing the SSL certificate used by the Config server

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_TRUST_STORE_PASSWORD

string

KeyStore to be used containing the SSL certificate for authentication with the Config server Can be either a classpath resource or a file system path

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_KEY_STORE

path

Password of KeyStore to be used containing the SSL certificate for authentication with the Config server

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_KEY_STORE_PASSWORD

string

Password to recover key from KeyStore for SSL client authentication with the Config server If no value is provided, the key-store-password will be used

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_KEY_PASSWORD

string

When using HTTPS and no keyStore has been specified, whether to trust all certificates

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_TRUST_CERTS

boolean

false

Custom headers to pass the Spring Cloud Config Server when performing the HTTP request

Environment variable: QUARKUS_SPRING_CLOUD_CONFIG_HEADERS

Map<String,String>

About the Duration format

The format for durations uses the standard java.time.Duration format. You can learn more about it in the Duration#parse() javadoc.

You can also provide duration values starting with a number. In this case, if the value consists only of a number, the converter treats the value as seconds. Otherwise, PT is implicitly prepended to the value to obtain a standard java.time.Duration format.