sábado, 27 de noviembre de 2021

Spring Boot Admin: Iniciación

Hoy vamos a ver una genial aplicación que nos permitirá monitorizar nuestras aplicaciones de Spring Boot, Spring Boot Admin a.k.a SBA.  Esta aplicación tiene múltiples cualidades pero para poder hacer uso de ellas, primero tenemos que configurarlo.  Y en este post nos centraremos en como configurarlo principalmente, primero con el método por defecto y luego haciendo uso de Eureka. Para ello, hemos utilizado las siguientes versiones:

  • Spring-boot: 2.5.7
  • Spring-admin: 2.5.4
  • Spring-cloud: 2020.0.3

Para empezar crearemos un servidor que será el encargado de recopilar la información y proporcionarnos una interfaz gráfica para acceder a los mismos. 

Vamos a empezar con una versión básica. Crearemos un servidor que se pueda registrar a si mismo. Para ello deberemos seguir los siguientes pasos:

  • Añadir la dependencia de spring spring-boot-starter-web
  • Añadir la dependencia de codecentric spring-boot-admin-starter-server que contendrá el motor del servidor.
  • Añadir la dependencia de codecentric spring-boot-admin-starter-client que nos permitirá conectar el propio servidor consigo mismo. 
  • Crear la clase de arranque y configuración con las anotaciones: @EnableAdminServer, @EnableAutoConfiguration, @SpringBootApplication.
  • Indicar a través de la propiedad spring.boot.admin.client.url en el fichero de configuración la ruta donde estará nuestra aplicación. Para el ejemplo: http://localhost:8080.
  • Indicar a través de la propiedad management.endpoints.web.exposure.include la habilitación de los endpoints de Actuator. 
Ya solo tenemos que arrancar la aplicación y podemos verla desplegada y auto descubierta. 


Con esto tendremos la configuración básica, pero tenemos que tener en cuenta que es una aplicación para la administración de otras aplicaciones. Y aunque en ciertos casos puede desplegarse dentro de una red interna donde no tendremos problemas de seguridad, también es posible que sea desplegado en entornos productivos y por tanto debe de tener algún tipo de seguridad, sobre todo si esta disponible desde Internet. Para ello añadiremos una configuración básica que nos permita incluir una pantalla de logín y un pequeño filtro de usuario. Y para llevarlo a cabo debemos realizar los siguientes pasos:
  • Añadimos la librería spring-boot-starter-security
  • En el fichero de configuración, añadimos las propiedades spring.security.user.name/passsword que configuren un usuario por defecto. 
  • En el fichero de configuración, añadimos las propiedades spring.boot.admin.client.username/password que permitan al cliente, el mismo, registrarse en el servidor
  • En el fichero de configuración, añadimos las propiedades spring.boot.admin.client.instance.metadata.user.name/password que permitan al servidor acceder a los endpoints securizados de métrica del cliente.
  • Además añadimos una clase java de configuración de seguridad que permita acceder sin restricciones a los endpoints info y health además de a la pantalla de login. Securizando el resto de URLs y endpoints de la aplicación. Configuración obtenida de la documentación oficial, aquí.
@Configuration(proxyBeanMethods = false)
public class SecuritySecureConfig extends WebSecurityConfigurerAdapter {
  private final AdminServerProperties adminServer;
  private final SecurityProperties security;

  public SecuritySecureConfig(AdminServerProperties adminServer, SecurityProperties security) {
    this.adminServer = adminServer;
    this.security = security;
  }
  @Override
  protected void configure(HttpSecurity http) throws Exception {
    SavedRequestAwareAuthenticationSuccessHandler successHandler = new SavedRequestAwareAuthenticationSuccessHandler();
    successHandler.setTargetUrlParameter("redirectTo");
    successHandler.setDefaultTargetUrl(this.adminServer.path("/"));

    http.authorizeRequests(
        (authorizeRequests) -> authorizeRequests.antMatchers(this.adminServer.path("/assets/**")).permitAll() 
            .antMatchers(this.adminServer.path("/actuator/info")).permitAll()
            .antMatchers(this.adminServer.path("/actuator/health")).permitAll()
            .antMatchers(this.adminServer.path("/login")).permitAll().anyRequest().authenticated() 
    ).formLogin(
        (formLogin) -> formLogin.loginPage(this.adminServer.path("/login")).successHandler(successHandler).and() 
    ).logout((logout) -> logout.logoutUrl(this.adminServer.path("/logout"))).httpBasic(Customizer.withDefaults()) 
        .csrf((csrf) -> csrf.csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse()) 
            .ignoringRequestMatchers(
                new AntPathRequestMatcher(this.adminServer.path("/instances"),
                    HttpMethod.POST.toString()), 
                new AntPathRequestMatcher(this.adminServer.path("/instances/*"),
                    HttpMethod.DELETE.toString()), 
                new AntPathRequestMatcher(this.adminServer.path("/actuator/**")) 
            ))
        .rememberMe((rememberMe) -> rememberMe.key(UUID.randomUUID().toString()).tokenValiditySeconds(1209600));
  }
  // Required to provide UserDetailsService for "remember functionality"
  @Override
  protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    auth.inMemoryAuthentication().withUser(security.getUser().getName())
        .password("{noop}" + security.getUser().getPassword()).roles("USER");
  }
}

Ahora al intentar acceder a la pantalla anterior veremos el formulario de acceso, en el cual deberemos indicar el usuario y contraseña indicados en el fichero de configuración:


Una vez que tenemos el servidor desplegado y securizado. Vamos a proceder a configurar un cliente que se pueda conectar a dicho servidor. La configuración es igual a la que hemos visto anteriormente:
  • Añadir la librería spring-boot-admin-starter-client.
  • En el fichero de configuración, añadimos las propiedades spring.boot.admin.client.username/password que permitan al cliente registrarse en el servidor.
  • En el fichero de configuración, indicar a través de la propiedad spring.boot.admin.client.url, la ruta donde estará nuestra aplicación. 
  • En el fichero de configuración, indicar a través de la propiedad management.endpoints.web.exposure.include la habilitación de los endpoints de Actuator. 
Y una vez que hemos arrancado la nueva aplicación, desde la pestaña Aplicaciones del menú de administración del SBA, podremos ver cuales son los clientes conectados al mismo. Además, clickeando sobre cualquiera de los clientes, podremos ver información detallada sobre dicha aplicación. 



Pero como estamos en un mundo donde los micro servicios dominan el panorama actual, ahora vamos a ver una configuración un poco más actual. Habilitando la configuración a través de un Service Discovery como Eureka. Para ello, crearemos un servidor Eureka, puedes ver el código de ejemplo aquí

Una vez que tenemos arrancado el servidor de Eureka, procederemos a realizar la configuración necesaria en el servidor de SBA. Para ello seguimos los siguientes pasos:
  • Añadimos la dependencia spring-cloud-starter-netflix-eureka-client, que nos permitirá conectarnos con el servidor de Eureka. Por tanto ya no es necesaria que utilicemos la librería spring-boot-admin-starter-client, ni las propiedades con el sufijo spring.boot.admin en el fichero de configuración.
  • Añadimos la dependencia spring-boot-starter-actuator en caso de que este como dependencia pasiva de otra librería. 
  • En el fichero de configuración, indicamos a través de la URL por defecto del servidor en la propiedad eureka.client.serviceUrl.defaultZone.
  • En el fichero de configuración, habilitamos que Eureka conozca el estado de la aplicación a través del endpoint health de la aplicación con la propiedad eureka.client.healthcheck.enabled.
  • En el fichero de configuración, indicamos las credenciales de seguridad para acceder a los endpoints securizados a través de las propiedades eureka.instance.metadata-map.user.name/password. Este paso solo es necesario si los endpoints se encuentran securizados.
Si hemos seguido los pasos correctamente tanto en el servidor SBA y en los clientes, al acceder a Eureka podremos visualizarlos los dos:


Y si accedemos al servidor SBA también podremos visualizar ambas aplicaciones en el mismo. 

Como siempre, si tenemos los conceptos más o menos claros, montar una aplicación con Spring Boot es bastante sencillo. Si quieres acceso al código visita el siguiente enlace

No hay comentarios:

Publicar un comentario