一、log4j日志的使用:

  1.log4j在Java代码中的使用:

 1 import org.apache.commons.logging.Log;
 2 import org.apache.commons.logging.LogFactory;
 3 
 4 public class BlogTest {
 5 
 6     /**
 7      * 得到log记录器的三种方式:
 8      *      1. 通过Log工厂:LogFactory。导包:commons-logging-1.1.3.jar, Log也是该包下的对应的类。
 9      *      2. 通过Logger的静态方法,有两种方式:导包:log4j-1.2.15.jar。
10      *          1)参数为配置的输出目的地名称appenderName(见后面配置中)
11      *          2)参数类对应为当前类的Class对象。
12      */
13     private static final Log logger = LogFactory.getLog(BlogTest.class);
14 //    private static Logger logger = Logger.getLogger("Console");
15 //    private static Logger logger = Logger.getLogger(BlogTest.class);
16 
17     public static void main(String[] args) {
18         int sum = 0;
19         try {
20             for(int i = 1; i < 11; i++){
21                 sum += i;
22             }
23             logger.info("计算得出了从1加到10的和成功,计算的结果为:" + sum);
24             int dev = sum / 0;
25         } catch (Exception e) {
26             logger.error("此处发生错误",new ArithmeticException("除0异常"));
27         }
28     }
29 }

  2. 运行结果:

  

 

  3. 为什么使用log4j,不使用system.out:

    log4j可以将程序运行产生的日志输出到控制台, 文件, 邮件, 数据库等很多不同的地方,不再局限与控制台。 这样, 部署后的程序虽然与IDE分离, 遇到错误同样可以通过从文件等目的地查看日志分析。而且, 这些不同的目的地,可以通过一个配置文件进行配置, 不需要修改源码。使用system.out只能再开发过程中使用控制台看到, 部署代码时, 还需要将不必要的输出语句注释掉。

    就算只针对控制台,如果发生错误或者是记录日志, log4j可以通过简单的配置准确地记录发生错误的类,位置, 时间。而system.out只是输出的一句话。

  4. 只含有以上代码, log4j是无法工作的, 必须有配套的配置文件, 来配置logger.error(“XXX”),logger.info(“XXX”)等往哪输出, 以什么样的格式输出。 

二、log4j的配置文件 

 1 ###########################根logger配置开始######################################
 2 log4j.rootLogger=[level], appenderName1,appenderName2......
 3 
 4 ### 1. 根logger配置,作用:配置全局logger级别以及输出目的地。即项目中所有日志的级别以及输出目的地, 包括引入的第三方jar包(有些框架或jar包中,也有日志的记录)。
 5 ###     1.1 level:日志级别
 6 ###             日志级别分类:
 7 ###                 ALL:打开所有日志记录开关;是最低等级的,用于打开所有日志记录。
 8 ###                 DEBUG:输出调试信息;指出细粒度信息事件对调试应用程序是非常有帮助的。
 9 ###                 INFO :输出提示信息;消息在粗粒度级别上突出强调应用程序的运行过程。
10 ###                 WARN :输出警告信息;表明会出现潜在错误的情形。
11 ###                 ERROR:输出错误信息;指出虽然发生错误事件,但仍然不影响系统的继续运行。
12 ###                 FATAL:输出致命错误;指出每个严重的错误事件将会导致应用程序的退出。
13 ###                 OFF :关闭所有日志记录开关;是最高等级的,用于关闭所有日志记录。
14 ###             日志级别排序(由高到低):
15 ###                 OFF > FATAL > ERROR > WARN > INFO > DEBUG > ALL
16 ###             常用日志级别:
17 ###                 ERROR > WARN > INFO > DEBUG
18 ###     1.2 appenderName:输出目的地的命名, 可以指定多个, 可以自定义命名
19 ###########################根logger配置结束#######################################
20 
21 #############################项目logger配置开始#########################################
22 log4j.logger.package1=[level], appenderName3,appenderName4......
23 log4j.logger.package2=[level], appenderName5,appenderName6......
24 ### 2. 特定包logger配置, 作用:如果自己写的某个包下日志, 不想按照全局配置的log级别或者想单独输出到某个文件, 使用此配置。
25 ###         2.1 level日志级别, 同根logger的取值范围一样(共7个, 常用4个), 可以和根logger相同, 可以不同。
26 ###         2.2 appenderName:输出目的地的命名, 可以和根logger输出目的地相同, 也可以为每个包单独定义输出目的地。
27 ###         2.3 如果这里配置的级别高于根logger级别, 则按照此处配置的日志级别。 如果低于根logger级别, 则按照根logger级别进行日志开关。
28 #############################项目logger配置结束#########################################
29 
30 ############################项目输出源(appender)标志位配置开始###################################
31 log4j.additivity.package1=boolean
32 log4j.additivity.package2=boolean
33 ### 3. 特定包的输出源标志位配置, 作用:配置特定包的输出源是否在根logger配置的输出源中输出, 默认是true
34 ###         例如:根logger(rootLogger)配置的输出源(appender)是appenderName1, package1包下的日志输出源是appenderName3。如果log4j.additivity.package1=boolean
35 ###              配置成false, 则package1下产生的日志, 只会在appenderName3配置的目的地输出。如果配置成true,会在appenderName1和appenderName2中输出。
36 ############################项目输出源(appender)标志位配置结束###################################
37 
38 #########################输出源(appender)输出方式配置开始########################################
39 log4j.appender.appenderName=fully.qualified.name.of.appender.class
40 log4j.appender.appenderName.layout=fully.qualified.name.of.layout.class
41 log4j.appender.appenderName.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
42 log4j.appender.appenderName.Append=false
43 log4j.appender.appenderName.bufferSize=10000
44 log4j.appender.appenderName.encoding=UTF-8
45 log4j.appender.appenderName.MaxFileSize=1GB
46 log4j.appender.appenderName.MaxBackupIndex=5
47 log4j.appender.appenderName.Target=System.err
48 log4j.appender.appenderName.Threshold=ERROR
49 ### 4. 日志输出方式的配置,作用:配置日志以什么样的方式输出, 输出到哪。
50 ###         4.1 语法:log4j.appender.appenderName1 = fully.qualified.name.of.appender.class, 输出目的地配置,常见取值:
51 ###             1)org.apache.log4j.ConsoleAppender(控制台)
52 ###             2)org.apache.log4j.FileAppender(文件)
53 ###             3)org.apache.log4j.DailyRollingFileAppender(每天产生一个日志文件)
54 ###             4)org.apache.log4j.RollingFileAppender(文件大小到达指定尺寸的时候产生一个新的文件)
55 ###             5)org.apache.log4j.WriterAppender(将日志信息以流格式发送到任意指定的地方)
56 ###             6)org.apache.log4j.net.SMTPAppender(邮件)
57 ###             7)org.apache.log4j.jdbc.JDBCAppender(数据库)
58 ###         4.2 语法:log4j.appender.appenderName1.layout = fully.qualified.name.of.layout.class, 输出布局配置,常见取值:
59 ###             1)org.apache.log4j.HTMLLayout(以HTML表格形式布局),
60 ###             2)org.apache.log4j.PatternLayout(可以灵活地指定布局模式)
61 ###             3)org.apache.log4j.SimpleLayout(包含日志信息的级别和信息字符串)
62 ###             4)org.apache.log4j.TTCCLayout(包含日志产生的时间、线程、类别等等信息)
63 ###         4.3 布局为PatternLayout的输出格式:
64 ###             -X号: X信息输出时左对齐;
65 ###             %p: 输出日志信息优先级,即DEBUG,INFO,WARN,ERROR,FATAL,
66 ###             %d: 输出日志时间点的日期或时间,默认格式为ISO8601,也可以在其后指定格式,比如:%d{yyy MMM dd HH:mm:ss,SSS},输出类似:2002年10月18日 22:10:28,921
67 ###             %r: 输出自应用启动到输出该log信息耗费的毫秒数
68 ###             %c: 输出日志信息所属的类目,通常就是所在类的全名
69 ###             %t: 输出产生该日志事件的线程名
70 ###             %l: 输出日志事件的发生位置,相当于%C.%M(%F:%L)的组合,包括类目名、发生的线程,以及在代码中的行数。举例:Testlog4.main (TestLog4.java:10)
71 ###             %x: 输出和当前线程相关联的NDC(嵌套诊断环境),尤其用到像java servlets这样的多客户多线程的应用中。
72 ###             %%: 输出一个"%"字符
73 ###             %F: 输出日志消息产生时所在的文件名称
74 ###             %L: 输出代码中的行号
75 ###             %m: 输出代码中指定的消息,产生的日志具体信息
76 ###             %n: 输出一个回车换行符,Windows平台为"/r/n",Unix平台为"/n"输出日志信息换行
77 ###
78 ###             可以在%与模式字符之间加上修饰符来控制其最小宽度、最大宽度、和文本的对齐方式。如:
79 ###                 1)%20c:指定输出category的名称,最小的宽度是20,如果category的名称小于20的话,默认的情况下右对齐。
80 ###                 2)%-20c:指定输出category的名称,最小的宽度是20,如果category的名称小于20的话,"-"号指定左对齐。
81 ###                 3)%.30c:指定输出category的名称,最大的宽度是30,如果category的名称大于30的话,就会将左边多出的字符截掉,但小于30的话也不会有空格。
82 ###                 4)%20.30c:如果category的名称小于20就补空格,并且右对齐,如果其名称长于30字符,就从左边较远输出的字符截掉。
83 ###         4.4 输出方式参数:
84 ###             1)log4j.appender.appenderName.Append=false:如果日志目的地是文件, 新产生日志是追加还是覆盖
85 ###             2)log4j.appender.appenderName.encoding:日志输出时的编码
86 ###             3)log4j.appender.appenderName.bufferSize=10000,因为产生日志写入到磁盘中的, 为提升性能可以先写入到缓存中,再往磁盘中写。
87 ###             4)log4j.appender.appenderName.MaxFileSize,如果日志目的地是文件, 则文件大小最大是多少。
88 ###             5)log4j.appender.appenderName.MaxBackupIndex,每天产生一个日志文件或者当日志文件达到指定大小时生成新文件这两种情况下备份文件的个数。
89 ###             6)log4j.appender.appenderName.Target:取值system.err(标红)或system.out(正常).
90 ###             7)log4j.appender.appenderName.Threshold=ERROR:自定义日志级别,自定义包中的日志不想和全局根loggerr日志级别一样时设置。注意根级别要小于自定义的才生效。
91 #########################输出源(appender)输出方式配置结束########################################

三、log4j完整应用实例:

  1. 简单应用:

    a)配置文件

 1 ### 日志级别:DEBUG,即比DEBUG级别低的处于关闭状态, 输出目的地两个, 名称为Console和File, 可以自定义名称,AAA,bbb都行
 2 log4j.rootLogger=DEBUG, Console,File
 3 ### 对于输出源Console的配置,输出到控制台,通过配置输出格式灵活指定布局格式
 4 log4j.appender.Console=org.apache.log4j.ConsoleAppender
 5 log4j.appender.Console.layout=org.apache.log4j.PatternLayout
 6 log4j.appender.Console.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
 7 ### 对于输出源File的配置,输出到文件,通过配置输出格式灵活指定布局格式
 8 log4j.appender.File=org.apache.log4j.FileAppender
 9 log4j.appender.File.File=./mylog4j/logs/file.log
10 log4j.appender.File.layout=org.apache.log4j.PatternLayout
11 log4j.appender.File.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n

    b)java文件:

 1 import org.apache.log4j.Logger;
 2 public class ConsoleTest {
 3 
 4     private static Logger logger = Logger.getLogger(ConsoleTest.class);
 5     public static void main(String[] args) {
 6         logger.debug("调试 this is a debug message");
 7         logger.info("基本 this is an info message!!");
 8         logger.warn("警告 this is a warn message");
 9         logger.error("错误 this is an error message!!!");
10         logger.fatal("致命 this is an fatal message!!!");
11     }
12 }

    c)输出结果:

    控制台:因为日志级别为DEBUG, 所以常见级别日志处于打开状态, 输出。

    

    文件:因为日志级别为DEBUG, 所以常见级别日志处于打开状态, 输出。

    

  2)一般应用:

    a)配置文件

    

 1 ### 1.根日志配置 日志级别:DEBUG
 2 log4j.rootLogger=DEBUG, Console,File
 3 
 4 ### 2.自定义包日志配置
 5 ### 2.1 第一个自定义包:com.mylog4j.console 日志级别,INFO, 输出源名称ConsoleTest, 日志界别要比根日志级别高
 6 log4j.logger.com.mylog4j.console=INFO, ConsoleTest
 7 ### 2.2 第二个自定义包:com.mylog4j.file 日志级别,ERROR, 输出源名称FileTest,日志界别要比根日志级别高
 8 log4j.logger.com.mylog4j.file=INFO, FileTest
 9 
10 ### 3.自定义包输出源标志位配置, 默认是true
11 ### 3.1 第一个自定义包:com.mylog4j.console 是否从父类输出源输出:是。
12 log4j.additivity.com.mylog4j.console=true
13 ### 3.2 第一个自定义包:com.mylog4j.console 是否从父类输出源输出:否。
14 log4j.additivity.com.mylog4j.file=false
15 
16 ### 4. 对于根logger输出源Console的配置,输出到控制台,通过配置输出格式灵活指定布局格式
17 log4j.appender.Console=org.apache.log4j.ConsoleAppender
18 log4j.appender.Console.layout=org.apache.log4j.PatternLayout
19 log4j.appender.Console.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
20 
21 ### 5. 对于根logger输出源File的配置,输出到文件,通过配置输出格式灵活指定布局格式
22 log4j.appender.File=org.apache.log4j.FileAppender
23 log4j.appender.File.File=./mylog4j/logs/file.log
24 ### 5.1 产生新日志在此基础上追加, 默认是true
25 log4j.appender.File.Append=true
26 log4j.appender.File.layout=org.apache.log4j.PatternLayout
27 log4j.appender.File.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
28 
29 ### 6. 对于自定义包com.mylog4j.console 输出源ConsoleTest的配置,输出到控制台,通过配置输出格式灵活指定布局格式
30 log4j.appender.ConsoleTest=org.apache.log4j.ConsoleAppender
31 log4j.appender.ConsoleTest.layout=org.apache.log4j.PatternLayout
32 log4j.appender.ConsoleTest.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
33 ### 6.1 输出级别为ERROE, 标红字体输出。
34 log4j.appender.ConsoleTest.Target=System.err
35 log4j.appender.ConsoleTest.Threshold=ERROR
36 
37 ### 7. 对于自定义包com.mylog4j.file 输出源FileTest的配置,输出到文件,通过配置输出格式灵活指定布局格式
38 log4j.appender.FileTest=org.apache.log4j.FileAppender
39 log4j.appender.FileTest.File=./mylog4j/logs/fileTest.log
40 ### 7.1 产生新日志在此基础上覆盖, 默认是true
41 log4j.appender.FileTest.Append=false
42 log4j.appender.FileTest.layout=org.apache.log4j.PatternLayout
43 log4j.appender.FileTest.layout.ConversionPattern=%d [%t] %-5p %c(%L) - %m%n
44 log4j.appender.FileTest.Threshold=INFO

    b))java文件:ConsoleTest在com.mylog4j.console包下,FileTest在com.mylog4j.file包下。

 1 // 第一个Java文件
 2 package com.mylog4j.console;
 3 import org.apache.log4j.Logger;
 4 public class ConsoleTest {
 5 
 6     private static Logger logger = Logger.getLogger(ConsoleTest.class);
 7     public static void main(String[] args) {
 8         logger.debug("[ConsoleTest.class] 调试 this is a debug message");
 9         logger.info("[ConsoleTest.class] 基本 this is an info message!!");
10         logger.warn("[ConsoleTest.class] 警告 this is a warn message");
11         logger.error("[ConsoleTest.class] 错误 this is an error message!!!");
12         logger.fatal("[ConsoleTest.class] 致命 this is an fatal message!!!");
13     }
14 }
15 
16 
17 // 第二个Java文件
18 package com.mylog4j.file;
19 import org.apache.log4j.Logger;
20 public class FileTest {
21 
22     private static Logger logger = Logger.getLogger(FileTest.class);
23     public static void main(String[] args) {
24         logger.debug("[FileTest.class] this is a debug message");
25         logger.info("[FileTest.class] this is an info message!!");
26         logger.warn("[FileTest.class] this is a warn message");
27         logger.error("[FileTest.class] this is an error message!!!");
28         logger.fatal("[FileTest.class] this is an fatal message!!!");
29     }
30 }

    c)运行结果:

     第一个java文件运行控制台:

    

    第一个Java文件运行日志文件:file.log打印日志, fileTest.log为空。

    

    

    第二个java文件运行控制台:

    

    第二个java文件运行日志文件:file.log为空, fileTest.log打印日志。

    

    

  d)结果分析:

  对于第一个Java文件运行:

  • 虽然, 在根logger配置了日志级别为DEBUG(log4j.rootLogger=DEBUG, Console,File), 但是配置文件中配置了com.mylog4j.console包下的Java文件运行日志级别是INFO(log4j.logger.com.mylog4j.console=INFO, ConsoleTest), 因此无论是控制台,还是文件中,都看不到debug级别的日志。
  • 在配置文件中, 配置了com.mylog4j.console包下的Java文件输出源标志是true(log4j.additivity.com.mylog4j.console=true),也就是说, 这个包下的日志除了本身配置的输出源ConsoleTest(log4j.logger.com.mylog4j.console=INFO, ConsoleTest)外, 还会在根logger配置的输出源Console,File(log4j.rootLogger=DEBUG, Console,File)输出 。这就是为什么在控制台输出了两遍日志。但是这两遍日志并不是完全一样的。对于ConsoleTest输出源配置的输出方式, 日志级别重新定义成了ERROR而且标红显示(log4j.appender.ConsoleTest.Threshold=ERROR, log4j.appender.ConsoleTest.Target=System.err),所以在控制台看到的日志组成是, 白色的是根logger配置的Console输出源的输出方式,红色的是自定义包配置的ConsoleTest输出源的输出方式。对于文件来说,这个包本身配置了一个输出源ConsoleTest(log4j.logger.com.mylog4j.console=INFO, ConsoleTest), 这个输出源是在控制台输出(log4j.appender.ConsoleTest=org.apache.log4j.ConsoleAppender),而不会在文件中输出。所以在日志文件中日志只输出了一遍, 输出的这一遍是由根logger配置的File输出源的输出方式(log4j.appender.File=org.apache.log4j.FileAppender)。因为根日志输出源和自定义包的输出源都没有指定输出到fileTest.log中,因此fileTest.log没有记录日志。

   对于第二个Java文件运行: 

  • 同理,虽然, 在根logger配置了日志级别为DEBUG(log4j.rootLogger=DEBUG, Console,File), 但是配置文件中配置了com.mylog4j.file包下的Java文件运行日志级别是INFO(log4j.logger.com.mylog4j.file=INFO, ConsoleTest), 因此无论是控制台,还是文件中,都看不到debug级别的日志。
  • 不同的是,配置文件中, 配置了com.mylog4j.file包下的Java文件输出源标志是false(log4j.additivity.com.mylog4j.file=false), 也就是说, 这个包下的日志, 只会在本身配置的输出源中输出,即只会在FileTest中输出(log4j.logger.com.mylog4j.file=INFO, FileTest)。而FileTest配置的输出目的地是文件格式输出, 输出在fileTest.log文件中(log4j.appender.FileTest.File=./mylog4j/logs/fileTest.log), 因此在控制台和file.log中都看不到打印的日志。

四、未完待续

  时间有限, 只是总结了最最基础的log4j的使用, 还有将日志每天输出一次, 或者是记录日志的文件达到一定程度时产生新文件,将日志输出到邮件, 数据库等没有整理, 再就是对于web项目的log使用。 有时间了在整理吧。    

 

版权声明:本文为xuesm原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://www.cnblogs.com/xuesm/p/9392654.html