Tutoriales

Trabajando con Spring Cloud Config 

En esta entrada vamos a ver como mantener externa las configuraciones de nuestros distintos microservicios mediante la herramienta de Spring Cloud Config. Vamos a ver qué nos ofrece  de soporte del lado del servidor y del lado del cliente para la configuración externa en un sistema distribuido. 

Spring Cloud Config se basa en dos partes: por un lado tendrá el servidor, que se encarga de consultar las configuraciones en distintos repositorios, como puede ser ficheros de Git, base de datos SQL, entre otros; y por otro lado tenemos el cliente, que ira en cada una de las aplicaciones y se encarga de consultar las configuraciones necesarias al servidor y añadirla a nuestro servicio.

En la siguiente imagen podemos ver el esquema de como quedaría: 

Servidor de Spring Cloud Config

Como hemos comentado, una de las partes necesarias para tener la configuración externa es el servidor, en este caso Spring Cloud Config. Gracias a esta tecnología, podremos crear el servidor de una manera rápida y casi sin configuración, como vamos a ver a continuación.

Lo primero que deberemos hacer es añadir la dependencia correspondiente al archivo «pom.xml»:

<dependency> 
        <groupId>org.springframework.cloud</groupId> 
        <artifactId>spring-cloud-config-server</artifactId> 
        <version>${spring-cloud-config.version}</version> 
</dependency> 

Deberemos indicar la versión que añadir; en el momento de escribir esta entrada la versión más moderna disponible es la «2.2.4.RELEASE».

También es recomendable que por seguridad se añada seguridad a nuestra aplicación, por lo que podemos añadir la siguiente dependencia, nuevamente en el archivo «pom.xml»: 

<dependency> 
        <groupId>org.springframework.boot</groupId> 
        <artifactId>spring-boot-starter-security</artifactId> 
</dependency> 

Para incluir una configuración básica de seguridad, como puede ser el uso de un usuario y contraseña, incluiremos en el archivo de «application.yml»:

spring:   
  security: 
    user.name: username 
    user.password: password 

A continuación, veremos como configurar distintas fuentes de configuración, a las que consultará nuestro servidor. 

Desde un repositorio de Git

La primera opción que nos ofrece Spring Cloud Config es obtener las configuraciones desde un repositorio de Git, para lo que deberemos añadir la siguiente configuración en el archivo de «application.yml»: 

spring: 
  profiles.active: git 
  cloud: 
    config.server: 
      git: 
        uri: <URL_REPOSTORIO> 
        clone-on-start: true 
        username: <GIT_USER> 
        password: <GIT_PASSWORD/TOKEN> 

En el código anterior, deberemos actualizar las siguientes variables:

  • <URL_REPOSTORIO>: URL de nuestro repositorio de Git donde tengamos las configuraciones. 
  • <GIT_USER>:  usuario de Git que tenga acceso al repositorio .
  • <GIT_PASSWORD/TOKEN>:  contraseña o token de acceso del usuario de repositorio Git.

Estructura del repositorio

Dentro de nuestro repositorio de Git, debemos colocar los distintos ficheros de configuración de todas las aplicaciones, siguiendo esta estructura:  «{application_name}-{profile}.properties/yml».

En estos ficheros, añadimos todas las configuraciones, al igual que se haría con nuestro application.yml dentro del servicio. También se nos permite añadir labels, que serán configuradas en el cliente para preguntar a una especifica. En Git, éstas las definiremos mediante ramas, es decir, si nuestra aplicación pregunta por la label «latest», el servidor buscará la configuración en una rama llamada latest. Si no se indica una label desde el cliente, se buscará en la rama master. 

Desde una base de datos

Otra fuente de datos que se nos permite configurar es una base de datos, mediante JDBC. Para esto, lo primero que debemos hacer es añadir las dependencias de Spring JDBC y, en nuestro caso,  el driver de PostgreSQL en el archivo «pom.xml»: 

<dependency> 
        <groupId>org.springframework.boot</groupId> 
        <artifactId>spring-boot-starter-jdbc</artifactId> 
</dependency> 

<dependency> 
        <groupId>org.postgresql</groupId> 
        <artifactId>postgresql</artifactId> 
        <scope>runtime</scope> 
</dependency> 

También tendremos que añadir la configuración de Spring JDBC al archivo de «application.yml» para poder conectarnos a la base de datos: 

spring: 
  profiles.active: git 
  datasource: 
      url: jdbc:<DB_URL> 
      username: <DB_USER> 
      password: <DB_PASS> 
      driver-class-name: org.postgresql.Driver 

Como en otro caso anterior, tendremos que actualizar el contenido de este script con las siguientes variables:

  • <DB_URL>:  url de conexión a las base de datos, indicando el tipo y base de datos (por ejemplo:  jdbc:postgresql://localhost:5434/cloud-config).
  • <DB_USER>:  usuario con acceso a la base de datos.
  • <DB_PASS>:  contraseña del usuario de la base de datos.

Por ultimo, tendremos que añadir la configuración de spring cloud server al archivo de «application.yml»: 

spring: 
  profiles.active: jdbc 
  cloud: 
    config.server: 
      jdbc: 
        sql: SELECT PROP_KEY, VALUE from PROPERTIES where APPLICATION=? and PROFILE=? and LABEL=? 
        order: 1 

Vemos como sólo tenemos que añadir la consulta que queremos realizar a la BD. A continuación veremos una posible estructura de esta. 

Estructura de la base de datos 

La base de datos deberá tener una tabla con las siguientes columnas:

  • id
  • created_on (no es obligatoria, pero si recomendable)
  • application
  • profile
  • label
  • prop_key
  • value

Tanto «prop_key» como «value» deberán contener la clave de nuestra configuración y su valor. A continuación se muestra un posible ejemplo de esta base de datos: 

Cifrado de datos sensibles 

Existen ocasiones en las cuales, dentro de la configuración de nuestros proyectos, se incluyen datos sensibles. Para ello, Spring Cloud Config provee de mecanismos para poder cifrar y descifrar este tipo de datos.

Para ello, lo primero que tenemos que hacer es definir una clave de encriptación segura en un archivo «bootstrap.yml» de nuestro servidor de Spring Cloud Config. Un ejemplo podría ser: 

encrypt.key: Bz43j5qrwBJ6MlfXjumV3tdKt0eaKZzN 

Definido esta clave, nuestro servidor la utilizara para el cifrado y descifrado de nuestros datos. Los servidores de Spring Cloud Config cuentan con dos endpoints de apoyo «/encrypt» y «/decrypt» con los que podremos encriptar los datos sensibles que irán en nuestra fuente de datos (Git, BB.DD, etc.).  Para poder indicar que estos datos son unos datos cifrados, en los ficheros de configuración habría que añadir «{cipher}» delante de la cadena cifrada. Según si el fichero es un yml o un properties, se indicará de distinta manera: 

Para el archivo «yml»:  

example: 

text: '{cipher}FKSAJDFGYOS8F7GLHAKERGFHLSAJ' 

Para el archivo «application.properties»:

example.text: {cipher}FKSAJDFGYOS8F7GLHAKERGFHLSAJ 

Cliente

Para que un servicio hago uso de la configuración del servidor, primero deberemos añadir la dependencia de cliente de Spring Cloud Config al archivo «pom.xml»: 

<dependency> 
        <groupId>org.springframework.cloud</groupId> 
    	<artifactId>spring-cloud-starter-config</artifactId> 
    	<version>${spring-cloud-config.version}</version> 
</dependency> 

Como en el caso anterior, deberemos indicar la versión que añadir («2.2.4.RELEASE» en estos momentos).

A continuación, en el fichero «bootstrap.properties», incluiremos la configuración necesaria para la conexión con el servidor: 

spring.application.name=<APPLICATION_NAME> 
spring.profiles.active=development 
spring.cloud.config.uri=<CLOUD_CONFIG_URL> 
spring.cloud.config.username=<CLOUD_CONFIG_USER> 
spring.cloud.config.password=<CLOUD_CONFIG_PASS> 
spring.cloud.config.label=<CLOUD_CONFIG_LABEL> 

En el código anterior actualizaremos las siguientes variables:

  • <APPLICATION_NAME>:  nombre de la aplicación, debe coincidir con lo especificado en el server.
  • <CLOUD_CONFIG_URL>:  URL donde está desplegado nuestro servidor. 
  • <CLOUD_CONFIG_USER>: nombre de usuario en caso de que hayamos añadido seguridad.
  • <CLOUD_CONFIG_PASS>: contraseña del usuario.
  • <CLOUD_CONFIG_LABEL>: etiqueta por la que buscara el servidor.

Con esto, nuestro servicio ya buscaría las configuraciones en nuestro servidor de Spring Cloud Config. Un ejemplo seria el siguiente: 

Controller.java  

@Value("${example.profile}") 
    private String profile; 

En este caso, al String de «profile» se le añadiría el valor indicado por el servidor, que consultaría en Git o en PostgreSQL (o en cualquiera configurado).


Imagen de cabecera: adaptada de Anthony Tori en Unsplash

✍🏻 Author(s)

Deja una respuesta