Fazendo login no Spring Boot

Fazendo login no Spring Boot

1. Visão geral

Neste breve tutorial, vamos explorar as principais opções de registro disponíveis no Spring Boot.

Informações mais detalhadas sobre Logback estão disponíveis emA Guide To Logback, enquanto Log4j2 é introduzido emIntro to Log4j2 – Appenders, Layouts and Filters.

Leitura adicional:

Definindo o nível de log na inicialização do Spring ao testar

Para quando você precisar diagnosticar falhas de teste examinando uma saída de log mais detalhada, veja como reconfigurar o log nos aplicativos Spring no momento do teste.

Read more

Exibir relatório de configuração automática na inicialização do Spring

Saiba quais beans são configurados automaticamente no aplicativo Spring Boot, gerando um relatório de configuração automática durante a inicialização.

Read more

2. Configuração inicial

Vamos primeiro criar um módulo Spring Boot - a maneira recomendada de fazer isso é usandoSpring Initializr, que abordamos em nossoSpring Boot Tutorial.

Agora vamos criar nosso único arquivo de classe,LoggingController:

@RestController
public class LoggingController {

    Logger logger = LoggerFactory.getLogger(LoggingController.class);

    @RequestMapping("/")
    public String index() {
        logger.trace("A TRACE Message");
        logger.debug("A DEBUG Message");
        logger.info("An INFO Message");
        logger.warn("A WARN Message");
        logger.error("An ERROR Message");

        return "Howdy! Check out the Logs to see the output...";
    }
}

Depois de carregar o aplicativo da web,we’ll be able to trigger those logging lines by simply visiting http://localhost:8080/

3. Registro de configuração zero

O Spring Boot é uma estrutura muito útil - nos permite esquecer a maioria das definições de configuração, muitas das quais são ajustadas automaticamente.

No caso de registro, a única dependência obrigatória éApache Commons Logging.

Precisamos importá-lo apenas ao usar Spring 4.x (Spring Boot 1.x), uma vez que no Spring 5 (Spring Boot 2.x) ele é fornecido pelo módulospring-jcl do Spring Framework.

We shouldn’t worry about importing spring-jcl at all if we’re using a Spring Boot Starter (o que quase sempre somos). Isso porque todo iniciador, como nossospring-boot-starter-web, depende despring-boot-starter-logging,, que já puxaspring-jcl para nós.

When using starters, Logback is used for logging by default.

O Spring Boot o pré-configura com padrões e cores ANSI para tornar a saída padrão mais legível.

Vamos agora executar o aplicativo e visitar a páginahttp://localhost:8080/ e ver o que acontece no console:

image

Como podemos ver na imagem acima,the default logging level of the Logger is preset to INFO, meaning thatTRACE and DEBUG messages are not visible.

Para ativá-los sem alterar a configuração,we can pass the –debug or –trace arguments on the command line:

java -jar target/spring-boot-logging-0.0.1-SNAPSHOT.jar --trace

Spring Boot tambémgives us access to a more fine-grained log level setting via environment variables. Existem várias maneiras de conseguir isso.

Primeiro, podemos definir nosso nível de log nas opções da VM:

-Dlogging.level.org.springframework=TRACE
-Dlogging.level.com.example=TRACE

Alternativamente, se estivermos usando Maven, podemosdefine our log settings via the command line:

mvn spring-boot:run
  -Dspring-boot.run.arguments=--logging.level.org.springframework=TRACE,--logging.level.com.example=TRACE

Ao trabalhar com Gradle, podemos passar as configurações de log pela linha de comando. Isso exigirásetting the bootRun task. Feito isso, podemos executar o aplicativo:

./gradlew bootRun -Pargs=--logging.level.org.springframework=TRACE,--logging.level.com.example=TRACE

Se quisermos alterar o detalhamento permanentemente, podemos fazê-lo no arquivoapplication.properties conforme descritohere:

logging.level.root=WARN
logging.level.com.example=TRACE

Finalmente, podemoschange the logging level permanently by using our logging framework configuration file.

Mencionamos antes que o Logback é usado por padrão no Spring Boot Starter. Vamos ver como definir um fragmento de um arquivo de configuração Logback em que definimos o nível para dois pacotes separados:


É importante notar queif the log level for a package is defined multiple times usando as diferentes opções mencionadas acima, maswith different log levels, the lowest level will be used.

Portanto, considerando nossos exemplos acima, se definirmos os níveis de log usando Logback, Spring Boot e variáveis ​​de ambiente ao mesmo tempo, o nível de log seráTRACE, pois é o mais baixo entre os níveis solicitados.

4. Log de configuração de logback

Mesmo que a configuração padrão seja útil (por exemplo, para começar em tempo zero durante POCs ou experimentos rápidos), provavelmente não é suficiente para nossas necessidades diárias.

Vejamoshow to include a Logback configuration com uma cor e padrão de registro diferentes, com especificações separadas para a saída deconsoleefile e comrolling policy decente para evitar a geração de arquivos de registro enormes.

Em primeiro lugar, devemos buscar uma solução que permita lidar com nossas configurações de registro sozinhas, em vez de poluirapplication.properties,, que é comumente usado para muitas outras configurações de aplicativo.

When a file in the classpath has one of the following names, Spring Boot will automatically load it sobre a configuração padrão:

  • logback-spring.xml

  • logback.xml

  • logback-spring.groovy

  • logback.groovy

Spring recommends using the -spring variant sobre os simples sempre que possível, conforme descritohere.

Vamos escrever umlogback-spring.xml: simples




    

    
        
            
                %black(%d{ISO8601}) %highlight(%-5level) [%blue(%t)] %yellow(%C{1.}): %msg%n%throwable
            
        
    

    
        ${LOGS}/spring-boot-logger.log
        
            %d %p %C{1.} [%t] %m%n
        

        
            
            ${LOGS}/archived/spring-boot-logger-%d{yyyy-MM-dd}.%i.log
            
            
                10MB
            
        
    

    
    
        
        
    

    
    
        
        
    

E quando executamos o aplicativo, aqui está a saída:

 

image

Como podemos ver, agora ele registra mensagens deTRACEeDEBUG, e o padrão geral do console é textual e cromaticamente diferente do anterior.

Agora ele também faz logon em um arquivo em uma pasta/logs criada no caminho atual e o arquiva por meio de uma política contínua.

5. Log de configuração Log4j2

Embora o Apache Commons Logging esteja no centro e o Logback seja a implementação de referência fornecida, todos os roteamentos para as outras bibliotecas de log já estão incluídos para facilitar a troca para eles.

In order to use any logging library other than Logback, though, we need to exclude it from our dependencies.

Para cada iniciador como este (é o único em nosso exemplo, mas poderíamos ter muitos deles):


    org.springframework.boot
    spring-boot-starter-web

precisamos transformá-lo em uma versão simplificada e (apenas uma vez) adicionar nossa biblioteca alternativa, aqui através de um iniciador:


    org.springframework.boot
    spring-boot-starter-web
    
        
            org.springframework.boot
            spring-boot-starter-logging
        
    


    org.springframework.boot
    spring-boot-starter-log4j2

Nesse ponto, precisamos colocar no caminho de classe um arquivo nomeado como um dos seguintes:

  • log4j2-spring.xml

  • log4j2.xml

Imprimiremos por meio do Log4j2 (sobre SLF4J) sem modificações adicionais.

Vamos escrever umlog4j2-spring.xml: simples



    
        
            
        

        
            
                %d %p %C{1.} [%t] %m%n
            
            
                
                
                
                
            
        
    

    
        
        
            
            
        

        
        
    

E quando executamos o aplicativo, aqui está a saída:

 

image

Como podemos ver, a saída é bastante diferente da do Logback - uma prova de que estamos usando totalmente o Log4j2 agora.

Além da configuração XML, Log4j2 nos permite usar também uma configuração YAML ou JSON, conforme descritohere.

6. Log4j2 sem SLF4J

Também podemos usar o Log4j2 nativamente, sem passar pelo SLF4J.

Para fazer isso, devemos simplesmente usar as classes nativas:

import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.LogManager;
// [...]
Logger logger = LogManager.getLogger(LoggingController.class);

Não precisamos realizar nenhuma outra modificação na configuração padrão do Log4j2 Spring Boot.

Agora podemos explorar os novos recursos do Log4j2 sem ficar presos à interface SLF4J antiga, mas também estamos presos a esta implementação e precisaremos reescrever nosso código ao decidir mudar para outra estrutura de registro.

7. Registrando com Lombok

Nos exemplos, vimosso far, we’ve had to declare an instance of a logger de nossa estrutura de registro. Esse código padrão pode ser irritante, e podemos evitá-lo usando várias anotações introduzidas pelo Lombok.

Primeiro, precisaremos adicionar a dependência do Lombok em nosso script de compilação para trabalhar com ela:


    org.projectlombok
    lombok
    1.18.4
    provided

7.1. @Slf4j e@CommonsLog

As APIs de registro SLF4J e Apache Commons nos permitem a flexibilidade de alterar nossa estrutura de registro sem afetar nosso código.

E podemosuse Lombok’s @Slf4j and @CommonsLog annotations para adicionar a instância correta do logger em nossa classe:org.slf4j.Logger para SLF4J eorg.apache.commons.logging.Log para Apache Commons Logging.

Para ver essas anotações em ação, vamos criar uma classe semelhante aLoggingController, mas sem uma instância do logger. Nós o nomeamos comoLombokLoggingControllere anotamos com@Slf4j:

@RestController
@Slf4j
public class LombokLoggingController {

    @RequestMapping("/lombok")
    public String index() {
        log.trace("A TRACE Message");
        log.debug("A DEBUG Message");
        log.info("An INFO Message");
        log.warn("A WARN Message");
        log.error("An ERROR Message");

        return "Howdy! Check out the Logs to see the output...";
    }
}

Observe que ajustamos o snippet um pouco, usandolog como nossa instância de logger. Isso ocorre porque adicionar a anotação@Slf4j adiciona automaticamente um campo chamadolog.

ComZero-Configuration Logging,the application will use underlying logging implementation Logback para registro. Da mesma forma, a implementação do Log4j2 será usada para o log com o Log4j2-Configuration Logging.

Obtemos o mesmo comportamento quando substituímos a anotação@Slf4j por@CommonsLog.

7.2. @Log4j2

Podemos usar a anotação@Log4j2 para usar Log4j2 diretamente. Portanto, fazemos uma alteração simples emLombokLoggingController para usar@Log4j2 em vez de@Slf4j ou@CommonsLog:

@RestController
@Log4j2
public class LombokLoggingController {

    @RequestMapping("/lombok")
    public String index() {
        log.trace("A TRACE Message");
        log.debug("A DEBUG Message");
        log.info("An INFO Message");
        log.warn("A WARN Message");
        log.error("An ERROR Message");

        return "Howdy! Check out the Logs to see the output...";
    }
}

Além do log, há outras anotações do Lombok que ajudam a manter nosso código limpo e arrumado. Mais informações sobre eles estão disponíveis emIntroduction to Project Lombok, e também temos um tutorial emSetting up Lombok with Eclipse and IntelliJ.

8. Cuidado com o Java Util Logging

O Spring Boot também oferece suporte ao registro JDK, por meio do arquivo de configuraçãologging.properties.

No entanto, há casos em que não é uma boa ideia usá-lo. Dethe documentation:

Existem problemas conhecidos de carregamento de classe no Java Util Logging que causam problemas ao executar a partir de um 'jar executável'. Recomendamos que você o evite ao executar a partir de um 'jar executável', se possível.

Também é uma boa prática, ao usar o Spring 4, excluir manualmentecommons-logging em pom.xml, para evitar possíveis conflitos entre as bibliotecas de registro. Em vez disso, o Spring 5 lida com isso automaticamente, portanto, não precisamos fazer nada ao usar o Spring Boot 2.

9. JANSI no Windows

Enquanto sistemas operacionais baseados em Unix, como Linux e Mac OS X, suportam códigos de cores ANSI por padrão, em um console do Windows tudo será monocromático.

O Windows pode obter cores ANSI por meio de uma biblioteca chamada JANSI.

Devemos prestar atenção às possíveis desvantagens do carregamento de classe, no entanto.

Devemos importá-lo e ativá-lo explicitamente na configuração da seguinte maneira:


    
        true
        
            [%thread] %highlight(%-5level) %cyan(%logger{15}) - %msg %n
        
    
    

As seqüências de escape ANSI são suportadas nativamente em muitas plataformas, mas não são por padrão no Windows. To enable ANSI support add the Jansi jar to our application and set property log4j.skipJansi to false. Isso permite que Log4j use Jansi para adicionar códigos de escape ANSI ao gravar no console.

Note
Antes do Log4j 2.10, Jansi era habilitado por padrão. O fato de Jansi exigir código nativo significa queJansi can only be loaded by a single class loader. Para aplicativos da web, isso significathe Jansi jar has to be in the web container’s classpath. Para evitar causar problemas aos aplicativos da web, o Log4j não tentará mais carregar o Jansi automaticamente sem a configuração explícita do Log4j 2.10 em diante.

Também vale a pena saber que:

  • a página de documentaçãolayout contém informações úteis Log4j2 JANSI na seçãohighlight{pattern}{style}

  • enquanto o JANSI pode colorir a saída, o Banner do Spring Boot (nativo ou personalizado por meio do arquivobanner.txt) permanecerá monocromático

10. Conclusão

Vimos as principais maneiras de interagir com as principais estruturas de registro em um projeto Spring Boot.

Também exploramos as principais vantagens e armadilhas de cada solução.

Como sempre, o código-fonte completo está disponívelover on Github.