Your Web News in One Place

Help Webnuz

Referal links:

Sign up for GreenGeeks web hosting
April 8, 2023 02:28 am GMT

Configurando o Spring Boot Admin: Server e Client

Existem vrias formas de se monitorar sistemas distribudos e uma que me agrada bastante pela simplicidade de configurao e confiabilidade o Spring Boot Admin.

Nesse tutorial criaremos duas aplicaes utilizando o Spring Boot, uma que ser o servidor de monitoramento e a outra, o cliente que dever se registrar para ser monitorado.

Tambm vamos aproveitar para implementar uma camada de segurana utilizando o Spring Security e com o #Maven, poderemos fazer o build das aplicaes para serem executadas individualmente.

Verses utilizadas

  • Spring Boot: 2.7.10
  • Spring Boot Admin Server: 2.7.10
  • Spring Boot Admin Client: 2.7.10

Configurando o Servidor

Crie um projeto utilizando o Spring Initilizr com as seguintes dependncias:

  • Starter Web
  • Starter Security
  • Admin Starter Server

Image description

Confira se as dependncias relacionadas ao Spring Boot Admin foram adicionadas:

...<dependency>    <groupId>de.codecentric</groupId>    <artifactId>spring-boot-admin-starter-server</artifactId></dependency><dependency>    <groupId>de.codecentric</groupId>    <artifactId>spring-boot-admin-server-ui</artifactId></dependency>...

Adicione a anotao @EnableAdminServer em alguma classe de configurao:

...@EnableAdminServer@SpringBootApplicationpublic class SpringBootAdminServerApplication {    public static void main(String[] args) {        SpringApplication.run(SpringBootAdminServerApplication.class, args);    }}

Configure o comportamento da aplicao utilizando o arquivo application.yaml. Como adicionamos uma camada de segurana, devemos criar um nome de usurio e senha para logarmos no servidor e tambm ser necessrio configurar o login para comunicao entre servidor e cliente.

server:  port: 8081  servlet:    context-path: /admin-consolespring:  security:    user:      # Configura o login do servidor.      name: ${SBA_SERVER_USERNAME}      password: ${SBA_SERVER_PASSWORD}  boot:    admin:      client:        # Necessrios para que o cliente possa se registrar na api do servidor protegido.        username: ${SBA_SERVER_USERNAME}        password: ${SBA_SERVER_PASSWORD}        instance:          metadata:            user:              # Necessrios para que o servidor possa acessar os endpoints protegidos do cliente.              name: ${SBA_CLIENT_USERNAME}              password: ${SBA_CLIENT_PASSWORD}# LOGlogging:  file:    name: ${user.home}/logs/admin/sba-server.log  level:    root: info    web: info    dev.marksduarte: info    org.springframework: info  charset:    file: utf-8

Agora vamos configurar o Spring Security criando uma classe e desabilitando o proxy dos beans na anotao @Configuration(proxyBeanMethods = false), pois como vamos trabalhar com @Bean autocontido, podemos evitar o processamento da subclasse CGLIB.

Tambm vamos permitir os acessos s rotas de login e assets e desabilitar a proteo CSRF paras o mtodos HTTP POST e HTTP DELETE nas instncias dos clientes.

package dev.marksduarte.springbootadminserver;import de.codecentric.boot.admin.server.config.AdminServerProperties;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.http.HttpMethod;import org.springframework.security.config.Customizer;import org.springframework.security.config.annotation.web.builders.HttpSecurity;import org.springframework.security.web.SecurityFilterChain;import org.springframework.security.web.authentication.SavedRequestAwareAuthenticationSuccessHandler;import org.springframework.security.web.csrf.CookieCsrfTokenRepository;import org.springframework.security.web.util.matcher.AntPathRequestMatcher;@Configuration(proxyBeanMethods = false)public class SecurityConfig {    private final AdminServerProperties adminServer;    public SecurityConfig(AdminServerProperties adminServer) {        this.adminServer = adminServer;    }    @Bean    protected SecurityFilterChain filterChain(HttpSecurity http) throws Exception {        SavedRequestAwareAuthenticationSuccessHandler successHandler = new SavedRequestAwareAuthenticationSuccessHandler();        successHandler.setTargetUrlParameter("redirectTo");        successHandler.setDefaultTargetUrl(this.adminServer.path("/"));        http.authorizeHttpRequests(authorizeRequests -> authorizeRequests                        .requestMatchers(new AntPathRequestMatcher(this.adminServer.path("/assets/**")))                        .permitAll()                        .requestMatchers(new AntPathRequestMatcher(this.adminServer.path("/login")))                        .permitAll()                        .anyRequest()                        .authenticated())                .formLogin(formLogin -> formLogin.loginPage(this.adminServer.path("/login"))                        .successHandler(successHandler))                .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/**"))));        return http.build();    }}

Pronto, agora s rodar a aplicao e conferir se o Admin Server est acessvel atravs do endereo http://localhost:8081/admin-console e logar com o usurio e senha informados na configurao.

Configurando o Cliente

Crie um projeto utilizando o Spring Initilizr com as seguintes dependncias:

  • Starter Web
  • Starter Actuator
  • Starter Security
  • Admin Starter Client

Confira no seu arquivo pom.xml, se a dependncia do Spring Boot Admin Client e Spring Actuator foram adicionadas:

...<dependency>    <groupId>org.springframework.boot</groupId>    <artifactId>spring-boot-starter-actuator</artifactId></dependency><dependency>    <groupId>de.codecentric</groupId>    <artifactId>spring-boot-admin-starter-client</artifactId>    <version>2.7.10</version></dependency>...

Agora vamos configurar o sistema comeando pelo arquivo application.yaml:

## INFO ENDPOINT## Aqui configuramos as informaes sobre o sistema, como nome, descrio, verso e etc.info:  name: Spring Boot Admin Client  description: Sistema Cliente  version: @project.version@server:  port: 8080  servlet:    context-path: /admin-clientspring:  # Configurao bsica do Spring Security.  security:    user:      name: ${SBA_CLIENT_USERNAME}      password: ${SBA_CLIENT_PASSWORD}  boot:    admin:      client:        enabled: true        # URL do servidor que o cliente deve se registrar.        url: http://localhost:8081/admin-console        username: ${SBA_SERVER_USERNAME}        password: ${SBA_SERVER_PASSWORD}        instance:          # URL base para calcular o service-url com o qual se registrar. O caminho  inferido em tempo de execuo e anexado  url base.          service-base-url: http://localhost:8080          # Essas informaes so passadas ao servidor para que ele possa fazer o acesso aos endpoints do sistema cliente.          metadata:            user:              name: ${SBA_SERVER_USERNAME}              password: ${SBA_SERVER_PASSWORD}        auto-deregistration: true## APPapp:  cors-origins:    - http://localhost  cors-methods:    - GET    - POST    - PUT    - DELETE    - OPTIONS  cors-headers:    - Authorization    - Content-Type    - Content-Length    - X-Requested-With## ACTUATORmanagement:  info:    env:      # Desde o Spring Boot 2.6, o env info  desabilitado por padro.      enabled: true  endpoint:    health:      show-details: ALWAYS      enabled: true    shutdown:      enabled: true    logfile:      enabled: true      external-file: logs/sba-client.log  endpoints:    web:      exposure:        # Liberamos todos os endpoints, mas lembre-se, em produo no se deve fazer isso.        include: "*"      cors:        allowed-headers: ${app.cors-headers}        allowed-methods: ${app.cors-methods}        allowed-origins: ${app.cors-origins}## LOGlogging:  file:    name: logs/sba-client.log    path: logs  level:    root: info    web: info    dev.marksduarte: info  charset:    file: utf-8  logback:    rollingpolicy:      clean-history-on-start: true      max-file-size: 10MB

Para simplificar, vamos habilitar todas as requisies para os endpoints do "/actuator/**":

...@EnableWebSecurity@Configurationpublic class SecurityConfig {    @Bean    public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {        http.csrf()                .disable()                .authorizeHttpRequests()                .antMatchers("/actuator/**")                .permitAll();        return http.build();    }}

Bom, isso j suficiente para registar nossa aplicao cliente no servidor.

Mas caso acontea alguma exceo do tipo: HttpMessageNotWritableException ou um response error HTTP 416 ao tentar acessar o arquivo de log, no se assuste, isso pode acontecer caso seu sistema tenha alguma classe de configurao do Jackson que estenda WebMvcConfigurationSupport.

Nesse caso, essa classe pode estar desativando a instanciao dos Beans com as configuraes padres do Spring Boot.

Para corrigir esse tipo de problema, podemos criar um Bean customizado e substituir a configurao padro criada na inicializao do sistema.

@Configurationpublic class JacksonConfig extends WebMvcConfigurationSupport {    private final Jackson2ObjectMapperBuilder builder = Jackson2ObjectMapperBuilder.json();    private static final List<MediaType> MEDIA_TYPE_LIST = List.of(            MediaType.ALL,            MediaType.parseMediaType("application/vnd.spring-boot.actuator.v2+json")    );    @Bean    public MappingJackson2HttpMessageConverter customMappingJackson2HttpMessageConverter() {        MappingJackson2HttpMessageConverter converter = actuatorConverter();        converter.setSupportedMediaTypes(MEDIA_TYPE_LIST);        return converter;    }    private MappingJackson2HttpMessageConverter actuatorConverter() {        return new MappingJackson2HttpMessageConverter(builder.build()) {            @Override            protected boolean canWrite(MediaType mediaType) {                // O mtodo super, retorna true se for null.                // Assim evitamos a exceo _HttpMessageNotWritableException_ caso o Content-Type 'null' seja enviado.                return mediaType != null && super.canWrite(mediaType);            }        };    }    @Override    protected void extendMessageConverters(List<HttpMessageConverter<?>> converters) {        /*        Remove somente o MappingJackson2HttpMessageConverterpadro e substitui pelo customMappingJackson2HttpMessageConverter.         */        var defaultHttpConverterOpt = converters.stream()                .filter(MappingJackson2HttpMessageConverter.class::isInstance)                .findFirst();        defaultHttpConverterOpt.ifPresent(converters::remove);        converters.add(customMappingJackson2HttpMessageConverter());    }}

Image description

Image description

Por enquanto s. At mais! ;)


Original Link: https://dev.to/marksduarte/configurando-o-spring-boot-admin-server-e-client-hld

Share this article:    Share on Facebook
View Full Article

Dev To

An online community for sharing and discovering great ideas, having debates, and making friends

More About this Source Visit Dev To