Registro conveniente no SpringBoot + Log4j2 + Maven

Olá queridos Khabrovites.


O material apresentado no artigo é destinado a iniciantes e, possivelmente, economizará várias horas de pesquisa no StackOverFlow e em outros sites, a fim de obter um sistema de registro conveniente que ele próprio entenda onde efetuar logon - no console, arquivo ou logstash.


No início do projeto, sempre surge a tarefa de configurar corretamente o log, enquanto no ambiente local os logs devem ser exibidos no console e no arquivo por conveniência durante a depuração, e é extremamente indesejável enviar os logs para o console no servidor remoto, mas eles devem ser gravados no arquivo, logstash ou no banco de dados. E se você possui o Windows localmente e em uma máquina Linux remota, o endereço do local desse arquivo de log é diferente.


Portanto, há muitas situações em que você precisa corrigir constantemente a configuração do sistema de registro com as mãos, dependendo das circunstâncias externas.


Eu estava cansado de lembrar e comentar constantemente sobre anexadores e desenvolvi uma maneira de configurar o Log4j2 para que, dependendo do perfil Maven selecionado, apenas os anexos certos fossem automaticamente ativados.


Abaixo está uma instrução para configurar um projeto usando o Spring Boot + Maven + Log4j2, cujo resultado será um sistema de log configurado e dois anexos: CONSOLE e SOCKET.


Primeiramente, faremos alterações na configuração do Maven (pom.xml):
Nas variáveis ​​em todo o nível pom.xml, adicione o endereço do host para logstash-appender:


<properties> <logstash.host>logstashcsm.example.ru</logstash.host> </properties> 

Adicione as dependências necessárias para o trabalho:


 <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-logging</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-log4j2</artifactId> </dependency> </dependencies> 

Observe que excluímos a dependência do spring-boot-starter-logging do spring-boot-starter-web.


Configure perfis do Maven para gerenciar dinamicamente os anexos conectados. No nível de cada perfil, configuramos as variáveis logstash.port, logger.console.tresholdFilter, logger.socket.tresholdFilter .


 <profiles> <profile> <id>local</id> <properties> <logstash.port>10000</logstash.port> <logger.console.tresholdFilter>ALL</logger.console.tresholdFilter> <logger.socket.tresholdFilter>OFF</logger.socket.tresholdFilter> </properties> </profile> <profile> <id>dev</id> <properties> <logstash.port>10001</logstash.port> <logger.console.tresholdFilter>OFF</logger.console.tresholdFilter> <logger.socket.tresholdFilter>ALL</logger.socket.tresholdFilter> </properties> </profile> </profiles> 

logstash.port - a porta para a qual os logs devem ser enviados.
logger.console.tresholdFilter - o valor define o nível de filtragem dos logs exibidos no console. No nosso caso, ALL significa que os registros de log de todos os níveis serão exibidos no console do appender.
logger.socket.tresholdFilter - o valor define o nível de filtragem dos logs enviados para o logstash. DESLIGADO - significa que nenhum registro enviado a este aplicativo passará.


Agora precisamos fazer alterações em application.properties para que, a partir do arquivo Log4j2.xml, possamos acessar o valor das variáveis ​​especificadas em pom.xml:


logstash.host=@logstash.host@
logstash.port=@logstash.port@
logger.console.tresholdFilter=@logger.console.tresholdFilter@
logger.socket.tresholdFilter=@logger.socket.tresholdFilter@


E, finalmente, definimos a configuração do próprio Log4j2 no arquivo log4j2.xml:


 <?xml version="1.0" encoding="UTF-8"?> <Configuration> <Properties> <Property name="socket.host">${bundle:application:logstash.host}</Property> <Property name="socket.port">${bundle:application:logstash.port}</Property> <Property name="console.thresholdFilter">${bundle:application:logger.console.tresholdFilter}</Property> <Property name="socket.thresholdFilter">${bundle:application:logger.socket.tresholdFilter}</Property> </Properties> <Appenders> <Console name="CONSOLE" target="SYSTEM_OUT"> <ThresholdFilter level="${console.thresholdFilter}"/> <PatternLayout pattern="%d %-5p [%t] %c{10} - %m%n"/> </Console> <Socket name="SOCKET" host="${socket.host}" port="${socket.port}" immediateFlush="true"> <ThresholdFilter level="${socket.thresholdFilter}"/> <JSONLayout eventEol="true" compact="true"/> </Socket> <Async name="ASYNC"> <AppenderRef ref="CONSOLE"/> <AppenderRef ref="SOCKET"/> </Async> </Appenders> <Loggers> <Logger name="ru.example" level="debug" additivity="false"> <AppenderRef ref="ASYNC"/> </Logger> <Root level="error"> <AppenderRef ref="ASYNC"/> </Root> </Loggers> </Configuration> 

Agora, para chamar o criador de logs na sua classe, você precisa criar uma instância dele:


 private static Logger logger = LoggerFactory.getLogger(YourClass.class); 

e vire para ele:


 logger.info("   "); 

Isso é tudo. Agora, o registro funcionará levando em consideração o perfil do Maven que está ativo no projeto.
Observe que, na lista do arquivo log4j2.xml , são ru.example dois registradores - ru.example e root , e eles têm níveis diferentes de registro de eventos. O primeiro funcionará em todos os eventos gerados pelas classes a partir do ru.example.* e ru.example.* tudo no nível DEBUG, e o root logs root registrará eventos de absolutamente todas as classes, exceto do nível ERROR.
Ao mesmo tempo, para que as entradas não sejam duplicadas nos logs, a configuração additivity="false" é usada.

Source: https://habr.com/ru/post/pt413091/


All Articles