SpringBoot系列(6):SLF4J+logback进行日志记录

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接: https://blog.csdn.net/mu_wind/article/details/99830829


SLF4J 是一个用于日志系统的简单 Facade,允许最终用户在部署其应用时使用其所希望的日志系统。大概意思是指你只需要按统一的方式写记录日志的代码,而无需关心日志是通过哪个日志系统,以什么风格输出的,因为它们取决于部署项目时绑定的日志系统。

例如,在项目中使用了 SLF4J 记录日志,并且绑定了 Log4j(即导入相应的依赖),则日志会以 Log4j 的风格输出;后期需要改为以 Logback 的风格输出日志,只需要将 Log4j 替换成 Logback 即可,不用修改项目中的代码。

1 yml配置文件

Spring Boot项目的配置文件有 application.properties 文件和 application.yml 文件两种,而我个人比较喜欢用 yml 文件。
application.yml 文件中对日志的配置:

logging:
  config: logback.xml
  level:
    com.example.demo.dao: trace
  1. logging.config 用来指定项目启动的时候,读取哪个配置文件,这里指定的日志配置文件是根路径下的 logback.xml 文件。关于日志的相关配置信息,都放在了 logback.xml 文件中。
  2. logging.level 用来指定具体的 Mapper 中日志的输出级别,上面的配置表示 com.example.demo.dao 包下的所有 Mapper 日志输出级别为 Trace,会将操作数据库的 SQL 打印出来。开发时设置成 trace 方便定位问题,在生产环境上,将这个日志级别再设置成 error 级别即可。
  3. 常用的日志级别按照从高到低依次为:ERROR、WARN、INFO、DEBUG。

2 logback.xml常用配置详解

logback主要包含三个组成部分:Loggers(日志记录器)、Appenders(输出目的在)、root,如下图:
在这里插入图片描述

2.1 根节点(configuration)

logback.xml的根节点是<configuration>,它包含以下属性:

  1. scan:当此属性设置为true时,配置文件如果发生改变,将会被重新加载,默认值为true。
  2. scanPeriod:设置监测配置文件是否有修改的时间间隔,如果没有给出时间单位,默认单位是毫秒。当scan为true时,此属性生效。默认的时间间隔为1分钟。
  3. debug:当此属性设置为true时,将打印出logback内部日志信息,实时查看logback运行状态。默认值为false。

例如:

<configuration scan="true" scanPeriod="60 seconds" debug="false">  
      <!-- 其他配置省略-->  
</configuration>  

2.1.1 读取配置文件:springProperty

如果想在logback.xml中使用yml配置文件中的配置,需要借助springProperty。
yml配置文件:

log:
  level:
    root: info
    my: debug
  file: logs/mutest
  maxsize: 30MB

logback.xml:

<springProperty name="logFile" source="log.file"/>
<springProperty name="rootlevel" source="log.level.root"/>
<springProperty name="mylevel" source="log.level.my"/>
<springProperty name="maxFileSize" source="log.maxsize"/>

这样配置完后,logback.xml下文使用**${logFile}**即可引用yml配置文件中的log.file的值:logs/mutest。这样做,后续更改配置会方便很多。

2.1.2 设置上下文名称:contextName

contextName ,设置日志上下文名称,可以通过%contextName来打印日志上下文名称。每个logger都关联到logger上下文,默认上下文名称为“default”。但可以使用<contextName>设置成其他名字,用于区分不同应用程序的记录。一旦设置,不能修改。

<configuration scan="true" scanPeriod="60 seconds" debug="false">  
      <contextName>myAppName</contextName>  
      <!-- 其他配置省略-->  
</configuration>  

2.1.3 设置变量:property

用来定义变量值的标签,<property> 有两个属性,name和value;其中name的值是变量的名称,value的值时变量定义的值。通过定义的值会被插入到logger上下文中。定义变量后,可以使“${}”来使用变量。

例如使用<property>来定义日志的输出格式:

<configuration scan="true" scanPeriod="60 seconds" debug="false">  
    <property name="LOG_PATTERN" value="%date{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n" />
    <!-- 其他配置省略--> 
</configuration>

我们来看一下这个定义的含义,首先定义一个格式,命名为 “LOG_PATTERN”,各项含义如下:

  1. %date 表示日期
  2. %thread 表示线程名
  3. %-5level 表示级别从左显示 5 个字符宽度
  4. %logger{50} 表示 Logger 名字最长 50 个字符
  5. %msg 表示日志消息
  6. %n 是换行符

2.2 appender节点

appender格式化日志输出节点,有俩个属性name和class,class用来指定哪种输出策略,常用就是控制台输出策略和文件输出策略。
在这里插入图片描述
appender示例:

<appender name="file" class="ch.qos.logback.core.rolling.RollingFileAppender">
    <file>${logFile}-demo.log</file>
    <encoder>
        <pattern>%d [%thread] %-5level %logger{36} -[%file:%line]- %msg%n</pattern>
        <charset>UTF-8</charset>
    </encoder>
    <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
  		<!-- 每天一归档 -->
  		<fileNamePattern>mylog-%d{yyyy-MM-dd}.%i.log</fileNamePattern>
   		<!-- 单个日志文件最多 100MB, 60天的日志周期,最大不能超过20GB -->
   		<maxFileSize>100MB</maxFileSize>    
   		<maxHistory>60</maxHistory>
   		<totalSizeCap>20GB</totalSizeCap>
	</rollingPolicy>
    
    <filter class="ch.qos.logback.classic.filter.LevelFilter">
        <level>error</level>
        <onMatch>ACCEPT</onMatch>
        <onMismatch>DENY</onMismatch>
    </filter>
</appender>

appender有以下子节点:

  1. name:appender的名称,在后文中被logger节点引用。一个logback配置文件中不能有重复的appender name。
  2. class:使用何种日志输出策略,上文示例中ch.qos.logback.core.rolling.RollingFileAppender表示使用文件回滚策略。另外,还有ConsoleAppender(控制台输出),FileAppender等策略。
  3. encoder和pattern:这两个节点组合用于具体输出的日志格式,具体见 2.1.2 设置变量:property
  4. file:该节点用来指明日志文件的输出位置,可以是绝对路径也可以是相对路径
  5. rollingPolicy:当发生滚动时,决定 RollingFileAppender 的行为,涉及文件移动和重命名。
  6. filter:日志输出拦截器,可以自定义拦截器也可以用系统一些定义好的拦截器

2.2.1 控制台输出

配置示例:

<configuration>  
  <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">  
    <encoder>  
      <!--引用前文property中的配置-->
      <pattern>${LOG_PATTERN}</pattern>  
    </encoder>  
  </appender>  
  
  <root level="DEBUG">  
    <appender-ref ref="STDOUT" />  
  </root>  
</configuration>  

2.2.1 rollingPolicy

rollingPolicy日志回滚策略,上面示例中使用了SizeAndTimeBasedRollingPolicy策略,有以下子节点:

  1. fileNamePattern:必须节点,可以用来设置指定时间的日志归档。上面示例中:mylog-%d{yyyy-MM-dd}.%i.log表示每天归档。如果想要归档周期长一些,比如每月归档,写成 mylog-%d{yyyy-MM}.%i.log 即可。
  2. maxHistory ,可选节点,控制保留的归档文件的最大数量,超出数量就删除旧文件,,例如设置为30的话,则30天之后,旧的日志就会被删除。
  3. maxFileSize:可选节点,指定单个日志文件的大小
  4. totalSizeCap,可选节点,用来指定日志文件的上限大小,例如设置为3GB的话,那么到了这个值,就会删除旧的日志。
  5. 当发生滚动时,决定 RollingFileAppender 的行为,涉及文件移动和重命名。

2.2.2 filter

filter,日志输出拦截器,可以自定义拦截器也可以用系统一些定义好的拦截器。
自定义日志拦截器示例:

/**
 1. @author guozhengMu
 2. @version 1.0
 3. @date 2019/8/20 20:13
 4. @description 日志输出拦截器
 5. @modify
 */
public class MyFilter extends Filter<ILoggingEvent> {

	@Override
	public FilterReply decide(ILoggingEvent event) {

    	if (event.getMessage().contains("error")) {
        	return FilterReply.ACCEPT; //允许输出
    	} else {
        	return FilterReply.DENY; //不允许输出
    	}
	}
}

系统定义的拦截器示例:

<filter  class="ch.qos.logback.classic.filter.ThresholdFilter">
	<level>ERROR</level>
</filter>

2.3 root节点

root节点,是必选节点,用来指定最基础的日志输出级别,他有两个点可以用来应用appender,格式化日志输出。

<root level="debug">
	<appender-ref ref="console" />
	<appender-ref ref="file" />
</root>

2.4 logger节点

logger节点,可选节点,用来具体指明包的日志输出级别,它将会覆盖root的输出级别。
示例:

<!-- name 属性表示匹配的logger类型前缀 -->  
<logger name="com.mutest.demo">  
    <level value="INFO" />  
    <!-- 引用的appender,类似于spring的ref -->  
    <appender-ref ref="FILE" />  
</logger>  
  1. name:指定具体包,该包下的日志输出将遵从该logger规定配置
  2. level:日志输出级别,该级别将覆盖root配置的输出级别。
  3. appender-ref:引用的appender,引用后将实现appender中定义的行为,例如上面示例中引用了【FILE】这个appender,那么【com.mutest.demo】中打印的日志将按【FILE】的配置进行记录。一个logger可以有多个引用,互不影响。

3 完整demo

<?xml version='1.0' encoding='UTF-8'?>
<configuration>
    <!--source读取自配置文件-->
    <springProperty name="logFile" source="log.file"/>
    <springProperty name="rootlevel" source="log.level.root"/>
    <springProperty name="mylevel" source="log.level.my"/>
    <springProperty name="maxFileSize" source="log.maxsize"/>

	<property name="LOG_PATTERN" value="%date{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n" />
    <property name="FILE_PATH" value="D:/logs/course03/demo.%d{yyyy-MM-dd}.%i.log" />

	<!--控制台输出-->
    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>${LOG_PATTERN}</pattern>
            <charset>UTF-8</charset>
        </encoder>
    </appender>

	<!--文件输出-->
    <appender name="FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
        <file>${logFile}-demo.log</file>
        <encoder>
            <pattern>%d [%thread] %-5level %logger{36} -[%file:%line]- %msg%n</pattern>
            <charset>UTF-8</charset>
        </encoder>
        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
        	<!--每月生成一个日志文件-->
            <fileNamePattern>${logFile}.demo.%d{yyyy-MM}.%i</fileNamePattern>
            <maxFileSize>${maxFileSize}</maxFileSize>
        </rollingPolicy>
        <filter class="ch.qos.logback.classic.filter.LevelFilter">
            <level>error</level>
            <onMatch>ACCEPT</onMatch>
            <onMismatch>DENY</onMismatch>
        </filter>
    </appender>

    <logger name="com.mutest.service.interfaces" level="${mylevel}" additivity="true">
        <appender-ref ref="FILE"/>
    </logger>

    <root level="${rootlevel}">
        <appender-ref ref="STDOUT"/>
    </root>

猜你喜欢

转载自blog.csdn.net/mu_wind/article/details/99830829