日志框架
SLF4J
说到日志不得不先说SLF4J,简单日志门面,对应的英文为Simple Logging Facade,是存取日志的标准接口,包括slf4j、log4j、jdk logging api和apache common-log等具体实现。
简单一点来说呢,他就是一个日志框架的接口,没有具体的日志实现,好处呢就是项目打日志的时候直接使用它,如果需要换具体的实现对代码也没有侵入只需要更换jar包和配置就好了,所以alibaba的编程规范中有下面这一条:
下面说一下实现需要导入的包
slf4j与log4j整合导入的jar包为
slf4j-api.jar
slf4j-log4j12.jar
log4j.jar
slf4j与log4j2整合导入的jar包为:
slf4j-api.jar
log4j-slf4j-impl.jar
log4j-api.jar
log4j-core.jar
slf4j与logback整合导入的jar包为:
slf4j-api.jar
logback-core.jar
logback-classic.jar
springboot
项目默认使用logback,如果需要使用log4j2的话对于springboot来说
首先要排除默认jar的依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
<exclusion>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
</exclusion>
</exclusions>
</dependency>
另外在application.yml中配置log4j配置文件的路径:
logging:
config: classpath:log4j2.xml
添加依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-log4j2</artifactId>
</dependency>
dubbo
dubbo默认使用log4j打印日志
找到dubbo中的LoggerFactory类有如下代码
static {
String logger = System.getProperty("dubbo.application.logger");
if ("slf4j".equals(logger)) {
setLoggerAdapter(new Slf4jLoggerAdapter());
} else if ("jcl".equals(logger)) {
setLoggerAdapter(new JclLoggerAdapter());
} else if ("log4j".equals(logger)) {
setLoggerAdapter(new Log4jLoggerAdapter());
} else if ("jdk".equals(logger)) {
setLoggerAdapter(new JdkLoggerAdapter());
} else {
try {
setLoggerAdapter(new Log4jLoggerAdapter());
} catch (Throwable e1) {
try {
setLoggerAdapter(new Slf4jLoggerAdapter());
} catch (Throwable e2) {
try {
setLoggerAdapter(new JclLoggerAdapter());
} catch (Throwable e3) {
setLoggerAdapter(new JdkLoggerAdapter());
}
}
}
}
}
可以通过增加启动参数
-Ddubbo.application.logger=slf4j
设置
log4j2 配置
<?xml version="1.0" encoding="UTF-8"?>
<configuration status="info">
<Properties>
<Property name="LOG_HOME">../logs</Property>
<Property name="DRUIDLOG_HOME">../druid-logs</Property>
<Property name="pattern">[%p] [%-d{yyyy-MM-dd HH:mm:ss,SSS}] %M(%L) | %m%n</Property>
<Property name="scheduleCron">0 0 0/2 * * ?</Property>
</Properties>
<Appenders>
<!-- 控制台输出 -->
<Console name="Console" target="SYSTEM_OUT">
<!-- 只输出level及以上级别的信息(onMatch),其他的直接拒绝(onMismatch) -->
<ThresholdFilter level="debug" onMatch="ACCEPT" onMismatch="DENY"/>
<!-- 输出日志的格式 -->
<PatternLayout
pattern="[%p] [%-d{yyyy-MM-dd HH:mm:ss,SSS}] %M(%L) | %m%n"/>
</Console>
<!--RollingRandomAccessFile 默认日志文件写入策略为异步刷盘,
引出一个缓冲区(buffer)的概念,RollingRandomAccessFile 会将日志信息先写入到缓冲区,
然后缓冲区满后刷到磁盘,并清空缓冲区,默认缓冲区的大小在8-256kb,
具体大小需要自己设置,所以说不会立即产生日志-->
<!-- ServerManager-ALL全量日志 滚动输出 -->
<RollingRandomAccessFile name="ServerManager-All"
immediateFlush="true" fileName="${LOG_HOME}/ServerManager.log"
filePattern="${LOG_HOME}/ServerManager-Info-%d{yyyy-MM-dd-HH}.log">
<PatternLayout>
<pattern>${pattern}</pattern>
</PatternLayout>
<Policies>
<!--按时间滚动-->
<TimeBasedTriggeringPolicy />
<!--按大小滚动-->
<SizeBasedTriggeringPolicy size="200 MB"/>
</Policies>
<CronTriggeringPolicy schedule="${scheduleCron}"/>
<!-- 最多备份30天以内的日志,此处为策略限制,Delete中可以按自己需要用正则表达式编写 -->
<!-- <DefaultRolloverStrategy>
<Delete basePath="${LOG_HOME}" maxDepth="1">
<IfFileName glob="ServerManager-Info.log.*.gz"/>
<IfLastModified age="30d"/>
</Delete>
</DefaultRolloverStrategy>-->
</RollingRandomAccessFile>
<!-- ServerManager-Info 滚动输出 -->
<RollingRandomAccessFile name="ServerManager-Info"
immediateFlush="true" fileName="${LOG_HOME}/ServerManager-Info.log"
filePattern="${LOG_HOME}/ServerManager-Info-%d{yyyy-MM-dd-HH}.log">
<!-- 只打印INFO -->
<ThresholdFilter level="WARN" onMatch="DENY" onMismatch="NEUTRAL"/>
<ThresholdFilter level="INFO" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout>
<pattern>${pattern}</pattern>
</PatternLayout>
<Policies>
<!--按时间滚动-->
<TimeBasedTriggeringPolicy />
<!--按大小滚动-->
<SizeBasedTriggeringPolicy size="200 MB"/>
</Policies>
<CronTriggeringPolicy schedule="${scheduleCron}"/>
</RollingRandomAccessFile>
<!-- ServerManager-Error错误日志 滚动输出 -->
<RollingRandomAccessFile name="ServerManager-Error"
immediateFlush="true" fileName="${LOG_HOME}/ServerManager-Error.log"
filePattern="${LOG_HOME}/ServerManager-Error-%d{yyyy-MM-dd-HH}.log">
<!-- 只打印ERROR -->
<ThresholdFilter level="ERROR" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout>
<pattern>${pattern}</pattern>
</PatternLayout>
<Policies>
<!--按时间滚动-->
<TimeBasedTriggeringPolicy />
<!--按大小滚动-->
<SizeBasedTriggeringPolicy size="200 MB"/>
</Policies>
</RollingRandomAccessFile>
<!-- DruidSql 滚动输出 -->
<RollingRandomAccessFile name="DruidSql"
immediateFlush="true" fileName="${D_HOME}/DruidSql.log"
filePattern="${D_HOME}/DruidSql-%d{yyyy-MM-dd-HH}.log">
<PatternLayout>
<pattern>[%d{yyyy-MM-dd HH:mm:ss,SSS}] [%t] [%p] [%c] - %m%n</pattern>
</PatternLayout>
<Policies>
<!--按时间滚动-->
<TimeBasedTriggeringPolicy />
<!--按大小滚动-->
<SizeBasedTriggeringPolicy size="200 MB"/>
</Policies>
</RollingRandomAccessFile>
</Appenders>
<Loggers>
<logger name="org.spring" level="error" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Error"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="org.springframework" level="error" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Error"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="org.apache.zookeeper" level="error" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Error"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="com.alibaba.dubbo" level="error" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Error"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="org.apache.zookeeper" level="info" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="com.alibaba.dubbo" level="info" additivity="false">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="druid.sql" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="DruidSql"/>
</logger>
<logger name="com.ibatis" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="com.ibatis.common.jdbc.SimpleDataSource" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="com.ibatis.common.jdbc.ScriptRunner" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="com.ibatis.sqlmap.engine.impl.SqlMapClientDelegate" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="java.sql.Connection" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="java.sql.Statement" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="java.sql.PreparedStatement" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<logger name="org.I0Itec.zkclient" level="info" additivity="false">
<AppenderRef ref="Console"/>
<appender-ref ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-All"/>
</logger>
<root level="info">
<AppenderRef ref="Console"/>
<AppenderRef ref="ServerManager-Info"/>
<AppenderRef ref="ServerManager-Error"/>
<AppenderRef ref="ServerManager-All"/>
</root>
</Loggers>
</configuration>