log4j.xml配置文件详解
log4j.xml配置文件中主要分为、、等一级标签,每个一级标签下又分为一些小标签,结构层次分明,配置简单,下面开始一一介绍。
Appender
Appender:日志输出器,配置日志的输出级别、输出位置等,包括以下几类:
- ConsoleAppender: 日志输出到控制台;
- FileAppender:输出到文件;
- RollingFileAppender:输出到文件,文件达到一定阈值时,自动备份日志文件;
- DailyRollingFileAppender:可定期备份日志文件,默认一天一个文件,也可设置为每分钟一个、每小时一个;
- WriterAppender:可自定义日志输出位置
log4j日志输出位置
<appender name="ConsoleAppender" class="org.apache.log4j.ConsoleAppender">(控制台)
<appender name="FileAppender" class="org.apache.log4j.FileAppender">(文件)
<appender name="DailyRollingFileAppender" class="org.apache.log4j.DailyRollingFileAppender">(每天产生一个日志文件)
<appender name="RollingFileAppender" class="org.apache.log4j.RollingFileAppender">(文件大小到达指定尺寸的时候产生一个新的文件)
<appender name="WriterAppender" class="org.apache.log4j.WriterAppender">(将日志信息以流格式发送到任意指定的地方)
下面贴出三个appender,分别为输出到控制台,输出到文件(文件大小到达指定尺寸的时候产生一个新的文件),输出到文件(每天产生一个日志文件,或者每小时,每分钟),其中标签param name=“Threshold” value=“ERROR” 设置为打印等级,优先级高于下面的logger标签,即如果appender中配置了ERROR,而下面有logger中配置了info并指向这个appender,那么,该日志打印的还是ERROR级别日志。
输出到控制台:
<appender name="CONSOLE" class="org.apache.log4j.ConsoleAppender">
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d{yyyy-MM-dd HH:mm:ss} [%p] %F - %m%n" />
</layout>
</appender>
输出到文件(文件大小到达指定尺寸的时候产生一个新的文件):
<appender name="Rolling" class="org.apache.log4j.RollingFileAppender">
<!--文件位置-->
<param name="File" value="d:/jdjc/Rolling/RollingFileAppender.log"/>
<!-- Append true,默认每次启动系统,日志继续输出到原来的文件,而不是清空了再来 -->
<param name="Append" value="true" />
<!-- MaxFileSize 后缀可以是KB, MB 或者是 GB. 在日志文件到达该大小时,将会自动滚动,即将原来的内容移到mylog.log.1文件 -->
<param name="MaxFileSize" value="10MB" />
<!-- MaxBackupIndex 最多1000个 ,多出1000个的日志文件会被自动清除-->
<param name="MaxBackupIndex" value="1000" />
<!--输出格式-->
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
输出到文件(每天产生一个日志文件,或者每小时,每分钟),
<appender name="dailyRollingAppender" class="org.apache.log4j.DailyRollingFileAppender">
<param name="File" value="d:/jdjc/Daily/RollingFileAppender.log"/>
<param name="Append" value="true" />
<param name="Threshold" value="ERROR" />
<!-- 设置日志备份频率,默认:为每天一个日志文件 -->
<param name="DatePattern" value="'.'yyyy-MM-dd'.log'" />
<!--每分钟一个备份-->
<!--<param name="DatePattern" value="'.'yyyy-MM-dd-HH-mm'.log'" />-->
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
log4j日志等级
Log4J日志等级包括:ALL,DEBUG, INFO, WARN, ERROR,FATAL,OFF;
log4j日志等级:ALL<DEBUG< INFO< WARN< ERROR<FATAL<OFF,等级越低,输出的日志越详细,等级低的日志会默认输出等级高的日志的内容,但是并不一定是等级越低越高,因为如果输出的日志越多,首先占用系统空间,第二很难定位到具体想要查看的日志位置,所以
Log4J推荐使用:DEBUG, INFO, WARN, ERROR级别日志。
log4j输出日志等级以及说明,按照从高到低顺序:
- OFF 为最高等级 关闭了日志信息
- FATAL 为可能导致应用中止的严重事件错误
- ERROR 为严重错误 主要是程序的错误
- WARN 为一般警告,比如session丢失
- INFO 为一般要显示的信息,比如登录登出
- DEBUG 为程序的调试信息
- TRACE 为比DEBUG更细粒度的事件信息
- ALL 为最低等级,将打开所有级别的日志
日志输出格式
Log4j日志输出格式有以下几种:
1.org.apache.log4j.HTMLLayout(以HTML表格形式布局),
2.org.apache.log4j.PatternLayout(可以灵活地指定布局模式),
3.org.apache.log4j.SimpleLayout(包含日志信息的级别和信息字符串),
4.org.apache.log4j.TTCCLayout(包含日志产生的时间、线程、类别等等信息)
我们最常用的log4j日志输出格式为org.apache.log4j.PatternLayOut,如下:
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
其参数意思:
%n - 换行
%m - 日志内容
%p - 日志级别(FATAL, ERROR,WARN, INFO,DEBUG or custom)
%r - 程序启动到现在的毫秒数
%t - 当前线程名
%d - 日期和时间, 一般使用格式 %d{yyyy-MM-dd HH:mm:ss, SSS}
%l - 输出日志事件的发生位置, 同 %F%L%C%M
%F - java 源文件名
%L - java 源码行数
%C - java 类名,%C{1} 输出最后一个元素
%M - java 方法名
logger
自定义的一个logger ,additivity 这个默认是true,即继承父类 root logger,这里是false,即不遵循root定义,走自己的定义方式,appender-ref 也就是说这个logger的输出目的地是哪里,ref就是关联到上面声明的appender,根据appender的定义输出方式和输出位置
以及logger 中定义的输出level和作用域(这里是com.ustc.jt包下面的日志)来输出日志。
<logger name="com.ustc.jt" additivity="true">
<!-- 输出级别是info级别及以上的日志 -->
<level value="info" />
<appender-ref ref="StreamOperateFile" />
<appender-ref ref="console" />
</logger>
root
根logger的设置,若代码中未找到指定的logger,则会根据继承机制,使用根logger。
这里关联两个appender,则会输出到两个appender定义的位置。
<root>
<level value="debug" />
<appender-ref ref="CONSOLE" />
<appender-ref ref="Rolling" />
</root>
下面贴出完整的log4j.xml配置供参考
示例一:三种输出方式的配置
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">
<appender name="CONSOLE" class="org.apache.log4j.ConsoleAppender">
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d{yyyy-MM-dd HH:mm:ss} [%p] %F - %m%n" />
</layout>
</appender>
<appender name="FILE" class="org.apache.log4j.RollingFileAppender">
<param name="File" value="d:/jdjc/Rolling/RollingFileAppender.log"/>
<param name="Append" value="true" />
<param name="MaxBackupIndex" value="1000" />
<param name="MaxFileSize" value="10MB" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
<appender name="dailyRollingAppender" class="org.apache.log4j.DailyRollingFileAppender">
<param name="File" value="d:/jdjc/Daily/RollingFileAppender.log"/>
<param name="Append" value="true" />
<!-- 设置日志备份频率,默认:为每天一个日志文件 -->
<!--<param name="DatePattern" value="'.'yyyy-MM-dd'.log'" />-->
<!--每分钟一个备份-->
<param name="DatePattern" value="'.'yyyy-MM-dd-HH-mm'.log'" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
<logger name="org.springframework">
<level value="error" />
</logger>
<logger name="org.springframework.security">
<level value="error" />
</logger>
<logger name="com.alibaba.dubbo">
<level value="error" />
</logger>
<logger name="org.apache.zookeeper">
<level value="error" />
</logger>
<logger name="com.ustcsoft.jt" additivity="false">
<level value="ERROR" />
<appender-ref ref="FILE" />
<appender-ref ref="dailyRollingAppender" />
</logger>
<root>
<level value="debug" />
<appender-ref ref="CONSOLE" />
</root>
</log4j:configuration>
示例二:根据等级不同,将info,error输出到不同的路径保存
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/">
<appender name="CONSOLE" class="org.apache.log4j.ConsoleAppender">
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d{yyyy-MM-dd HH:mm:ss} [%p] %F - %m%n" />
</layout>
</appender>
<appender name="dailyRollingAppenderForError" class="org.apache.log4j.DailyRollingFileAppender">
<param name="File" value="f:/ezLog/jdjc/Error/jdjc.log"/>
<param name="Append" value="true" />
<param name="Threshold" value="ERROR" />
<param name="DatePattern" value="'.'yyyy-MM-dd'.log'" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
<appender name="dailyRollingAppenderForDebug" class="org.apache.log4j.DailyRollingFileAppender">
<param name="File" value="f:/ezLog/jdjc/Debug/jdjc.log"/>
<param name="Append" value="true" />
<param name="DatePattern" value="'.'yyyy-MM-dd'.log'" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%d{yyyy-MM-dd HH:mm:ss:SSS}] [%-5p] [method:%l]%n%m%n%n" />
</layout>
</appender>
<logger name="org.springframework">
<level value="error" />
</logger>
<logger name="org.springframework.security">
<level value="error" />
</logger>
<logger name="com.alibaba.dubbo">
<level value="error" />
</logger>
<logger name="org.apache.zookeeper">
<level value="error" />
</logger>
<logger name="com.ustcsoft.jt" additivity="false">
<level value="info" />
<appender-ref ref="dailyRollingAppenderForDebug" />
<appender-ref ref="dailyRollingAppenderForError" />
</logger>
<root>
<level value="debug" />
<appender-ref ref="CONSOLE" />
</root>
</log4j:configuration>
java代码中的配置
我们知道,系统运行过程中如果抛出异常,我们一般会try,catch进行捕获,但是一般这种方式是能预测到这里可能会抛出异常,但是有些异常是运行时抛出来的,比如空指针,数组下标越界等,这是我们需要定义一个系统全局异常捕获机制,通过@ExceptionHandler注解实现,切记,这里输出日志文件时: logger.error(“系统异常” + e.getMessage(),e); 是两个参数,如果第二个参数e不写,则无法定位到具体抛出异常的位置。
package com.ustcsoft.jt.controller;
import com.ustcsoft.framework.vo.Result;
import org.apache.log4j.Logger;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
@ControllerAdvice
public class GloableExceptionController {
private final Logger logger = Logger.getLogger(this.getClass());
@ExceptionHandler({Exception.class})
@ResponseBody
public Result sqlException(Exception e) {
//向控制台打印错误的堆栈信息
e.printStackTrace();
//向log4j.xml中配置的位置输出日志文件
logger.error("系统异常" + e.getMessage(),e);
return new Result(false, "500", "服务器异常");
}
}
如果我们系统没有捕获到异常,那么,我们的控制台不会打印错误日志,那么这些异常怎么办呢?
系统中没有捕获到异常,会被tomcat捕获,并输出到tomcat的localhost.Y-M-D.log 日志中。