使用slf4j 和 logback 作为java日志的输出框架
slf4j是接口抽象层,logback是slf4j的具体实现,在程序中使用slf4j的api进行日志的记录。使用logback来配置日志的输出规则。
<!-- jar包引用 -->
<!--<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.25</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.2.3</version>
</dependency>-->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.3</version>
</dependency>
创建logback的xml配置文件:
- logback 会在类路径下寻找名为 logback-test.xml 的文件。
- 如果没有找到,logback 会继续寻找名为 logback.groovy 的文件。
- 如果没有找到,logback 会继续寻找名为 logback.xml 的文件。
- 如果没有找到,将会通过 JDK 提供的 ServiceLoader 工具在类路径下寻找文件 META-INFO/services/ch.qos.logback.classic.spi.Configurator,该文件的内容为实现了
Configurator
接口的实现类的全限定类名。 - 如果以上都没有成功,logback 会通过 BasicConfigurator 为自己进行配置,并且日志将会全部在控制台打印出来。
最后一步的目的是为了保证在所有的配置文件都没有被找到的情况下,提供一个默认的(但是是非常基础的)配置。
如果你使用的是 maven,你可以在 src/test/resources 下新建 logback-test.xml。maven 会确保它不会被生成。所以你可以在测试环境中给配置文件命名为 logback-test.xml,在生产环境中命名为 logback.xml。
<?xml version="1.0" encoding="UTF-8"?>
<configuration >
<!-- 定义属性,定义后,可以通过${}取出值 -->
<!-- 这里定义的是日志文存储的物理路径,${catalina.base}是tomcat文件夹的根路径,如D:\apache-tomcat-7.0.90 -->
<property name="LOG_HOME" value="${catalina.base}/logs" />
<property name="PROJECT_NAME" value="LoansPlatform" />
<!-- name为定义的appender的名称,可以随便取, ch.qos.logback.core.ConsoleAppender 是指控制台输出 -->
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<!--
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
<level>info</level> <!-- 日志级别过滤,只处理info以上级别的日志 -->
</filter>
-->
<encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
<!--日志输出格式:
%d表示日期时间,
%thread表示线程名,
%‐5level:级别从左显示5个字符宽度
%file:打印该条日志所在的java类
%line:打印该条日志所在的java类的行号
%logger{50} 表示logger名字最长50个字符,否则按照句点分割。
%msg:日志消息,
%n是换行符
-->
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level [%file:%line] %logger{50} - %msg%n</pattern>
</encoder>
</appender>
<!-- 按照每天生成日志文件 -->
<appender name="FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${LOG_HOME}/${PROJECT_NAME}.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<!--日志文件输出的文件名,若文件名以.gz或.zip结尾则自动压缩-->
<FileNamePattern>${LOG_HOME}/${PROJECT_NAME}.log.%d{yyyy-MM-dd}.%i.log</FileNamePattern>
<!--日志文件保留天数-->
<MaxHistory>365</MaxHistory>
<!--日志文件最大的大小-->
<timeBasedFileNamingAndTriggeringPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedFNATP">
<maxFileSize>50MB</maxFileSize>
</timeBasedFileNamingAndTriggeringPolicy>
</rollingPolicy>
<encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level [%file:%line] %logger{50} - %msg%n</pattern>
<charset class="java.nio.charset.Charset">UTF-8</charset>
</encoder>
</appender>
<!-- 日志输出级别 -->
<!-- TRACE,DEBUG,INFO,WARN,ERROR,ALL,OFF -->
<!-- 默认的全局输出级别配置 -->
<root level="DEBUG">
<!-- 使用哪些appender的配置进行输出 -->
<appender-ref ref="STDOUT" />
<appender-ref ref="FILE" />
</root>
<!-- cn.fg.api包下的日志,使用error级别进行输出, addtivity="false"后,root就不会再输出,不然就会打印两次,因为logger是继承root的 -->
<logger name="cn.fg.api" level="ERROR" addtivity="false">
<appender-ref ref="FILE"></appender-ref>
</logger>
</configuration>
<!--
root logger level addtivity appender 的关系详解
1.我们把它当成java类来理解,root是父类,logger是继承root的子类,appender也是类,level和addtivity是root类中的属性
2.appender是指日志如何处理,比如控制台输出、文件输出等
3.logger的name属性是必须的,其他属性可以不填默认继承root
4.addtivity 是否向上传递,默认值为true。传递什么信息?这里传递的是appender而非level。
(1)向上指?cn.fg.api的向上就是cn.fg,如果找不到就指向root
(2)传递了又如何?传递后,如果父logger存在appender,就对日志做处理,否则查看addtivity,是否在向上传递。
注意:传递是不会考虑level的设置,即使父logger的level级别比子logger高,也是会执行appender的。这也是日志被打印了多次的原因(父子都设置了appender,addtivity=true)
-->
<root level="error">
<appender-ref ref="STDOUT" />
</root>
<logger name="cn.fg" level="info">
<appender-ref ref="STDOUT"></appender-ref> <!-- 默认向上传递 -->
</logger>
<logger name="cn.fg.api" level="trace" addtivity="false"> <!-- 不向上传递 -->
<appender-ref ref="STDOUT"></appender-ref>
</logger>
LoggerFactory.getLogger(getClass()).info("info");
LoggerFactory.getLogger(getClass()).error("error");
logback中文参考手册 http://www.logback.cn