您好,欢迎访问三七文档
log4j简明手册CekiGülcüMarch2002Copyright©2000-2004TheApacheSoftwareFoundation.版权所有。Log4j软件是在遵守ApacheSoftwareLicense1.1版的条例下发行的,ApacheSoftwareLicense的复制件被包括在log4j发布的LICENSE.txt文件里。这个简短手册也借用了Thecompletelog4jmanual里的一些内容,Thecompletelog4jmanual包含最新的更为详尽的信息。Thecompletelog4jmanual摘要这个文档资料描述了log4jAPI,它的独特的特性和设计原理。Log4j是由许多作者共同参与的开放源代码项目。它允许开发人员以任意的精细程度控制哪些日志说明被输出。通过使用外部的配置文件,可以在运行时配置它。最好的是,log4j开发包很容易上手。注意,它也可能会使一些开发人员着迷。简介几乎每个大的应用程序都有它自己的日志和跟踪程序的API。顺应这一规则,E.U.SEMPER项目组决定编写它自己的程序跟踪API(tracingAPI)。这开始于1996年早期。经过无数的工作,更改和性能加强,这个API终于成为一个十分受欢迎的Java日志软件包,那就是log4j。这个软件包的发行遵守opensource动议认证的ApacheSoftwareLicense。最新的log4j版本包括全部的源代码,类文件和文档资料,可以在找到它们。另外,log4j已经被转换成C,C++,C#,Perl,Python,Ruby,和Eiffel语言。把logstatements插入到你的代码中是一种排错的低技能办法。这也许是唯一的方法,因为排错工具并不总是可以被使用或者适用于你的程序。对于多线程的应用程序和多数发行的应用程序,通常就是这样的情形。经验告诉我们logging是开发过程中重要的一环。它具有多种优点。首先,它能精确地提供运行时的上下文(context)。一旦在程序中加入了Log代码,它就能自动的生成并输出logging信息而不需要人为的干预。另外,log信息的输出可以被保存到一个固定的地方,以备以后研究。除了在开发过程中发挥它的作用外,一个性能丰富的日志记录软件包能当作一个审计工具(audittool)使用。BrianW.Kernighan和RobPike在他们的ThePracticeofProgramming书中这样写到:ThePracticeofProgramming作为个人的选择,除了得到一大堆程序跟踪信息或一两个变量值以外,我们倾向於不使用排错器。一个原因是在详细而复杂的数据结构和控制流程中很容易迷失;我们发现认真思考并在关键处加入自我检查代码和输出指令,比起一步步看程序要效率高。在日志说明里查找比在明智地放置自我检查代码后的输出里查找要费时。而决定在哪里放置打印指令要比在日志说明里一步步找到关键的代码要省时间。更重要的是,自我检查的排错指令和程序并存;而排错sessions是暂时的。Logging确实也有它的缺陷。它降低了程序运行的速度。它太冗长,查看时很容易错过。为了减少这些负面影响,log4j被设计得可靠,高效和灵活。因为,记录日志很少是一个应用程序的主要焦点,log4jAPI尽量做到容易被理解和使用。Loggers,AppendersandLayoutsLog4j有三个主要组件:loggers,appenders和layouts。这三类组件一起应用,可以让开发人员能够根据日志的类型和级别进行记录,并且能在程序运行时控制log信息输出的格式和往什么地方输出信息。Loggerhierarchy任何loggingAPI与简单的System.out.println输出调试信息方法比较,最主要的优点在于它能够关闭一些调试信息输出而不影响其他人的调试。这种能力的实现是假设这些logging空间,也就是所有的可能发生的日志说明空间,可以根据程序开发人员选择的标准进行分类。这一观察以前使得我们选择了category作为这个软件包的中心概念。但是,在log4j1.2版本以后,Logger类取代了Category类。对于那些熟悉早先版本的log4j的开发人员来说,Logger类只不过是Category类的一个别名。Loggers是被命名的实体。Logger的名字大小写有区别(case-sensitive),并且它们遵守阶层式的命名规则:NamedHierarchy如果一个logger的名字后面跟着一个点号(dot),它就是点号(dot)后面的那个logger的前辈(ancestor),是这个晚辈(descendant)的前缀。如果在它自己和这个晚辈之间没有其它的前辈,它和这个晚辈之间就是父子关系。例如,叫做com.foo的logger是叫做com.foo.Bar的logger的父辈。同样地,java是java.util的父辈,是java.util.Vector的前辈。大多数开发人员都熟悉这种命名方法。com.foocom.foo.Barjavajava.utiljava.util.Vector根(root)logger位于logger阶层的最上层。它在两个方面很特别:1.它总是存在的,2.不能通过使用它的名字直接得到它。通过这个类的静态方法Logger.getRootLogger得到它(指RootLogger)。所有其他的loggers是通过静态方法Logger.getLogger来实例化并获取的。这个方法Logger.getLogger把所想要的logger的名字作为参数。Logger类的一些其它基本方法在下面列出:packageorg.apache.log4j;publicclassLogger{//Creationandretrievalmethods:publicstaticLoggergetRootLogger();publicstaticLoggergetLogger(Stringname);//printingmethods:publicvoiddebug(Objectmessage);publicvoidinfo(Objectmessage);publicvoidwarn(Objectmessage);publicvoiderror(Objectmessage);publicvoidfatal(Objectmessage);//genericprintingmethod:publicvoidlog(Levell,Objectmessage);}Loggers可以被指派优先级别。Level.html#DEBUGDEBUG,INFO,WARN,ERROR和FATAL这组级别在org.apache.log4j.Level类中有定义。你也可以通过Level类的子类去定义你自己的优先级别,尽管我们不鼓励你这样做。在后面我们会讲到一个更好的方法。如果一个logger没有被指定优先级别,它将继承最接近的祖先所被指定的优先级别。下面是更多关于优先级别的信息:LevelInheritance对于一个给定的loggerC,它继承的级别等于logger阶层里,从C开始往rootlogger上去的第一个non-null级别。要保证所有的loggers最终都继承一个优先级别,rootlogger总是有一个被指派的优先级。下面是具有各种指派优先级别值的四个表格,以及根据上面的规则所得出的继承优先级别。Loggername(名称)指派级别继承级别根ProotProotXnoneProotX.YnoneProotX.Y.ZnoneProot例子在上面的示例1中,只有rootlogger被指派了级别。这个级别的值,Proot,被其它的loggersX,X.Y和X.Y.Z继承了。Loggername(名称)指派级别继承级别根ProotProotXPxPxX.YPxyPxyX.Y.ZPxyzPxyz例子在上面的示例2中,所有的loggers都有一个指派的级别值。不需要级别继承。Loggername(名称)指派级别继承级别根ProotProotXPxPxX.YnonePxX.Y.ZPxyzPxyz例子在示例3中,loggersroot,X和X.Y.Z分别被指派级别值Proot,Px和Pxyz。LoggerX.Y从它的父辈X那里继承它的级别值。Logger指派继承name(名称)级别级别根ProotProotXPxPxX.YnonePxX.Y.ZnonePx例子在示例4中,loggersroot和X分别被指派级别值Proot和Px。LoggerX.Y和X.Y.Z继承它们最接近的父辈X的被指派的级别值。日志请求是通过调用一个日志实例的打印方法(之一)而产生的。这些打印方法是log4j/Logger.html#debug(java.lang.Object)debug,info,warn,error,fatal和log。根据定义,打印方法决定一个日志请求的级别。例如,如果c是一个日志实例,那么语句c.info(..)就是级别为INFO的一个日志请求。c.info(..)只有一个日志请求(Aloggingrequest)的级别高于或等于它的logger级别的时候才能够被执行。否则,则被认为这个日志请求不能被执行。一个没有被定义优先级别的logger将从层次关系中的前辈那里继承优先级别。这个规则总结如下:BasicSelectionRule在一个级别为q(被指定的或继承的)的logger里,一个级别为p的日志请求,只有在p=q时才能够被执行。这个规则是log4j的核心。它假设级别是有先后顺序的。对于标准的优先级别来说,DEBUGINFOWARNERRORFATAL。这里是一个关于这个规则的例子://getaloggerinstancenamedcom.fooLoggerlogger=Logger.getLogger(com.foo);//Nowsetitslevel.Normallyyoudonotneedtosetthe//levelofaloggerprogrammatically.Thisisusuallydone//inconfigurationfiles.logger.setLevel(Level.INFO);Loggerbarlogger=Logger.getLogger(com.foo.Bar);//Thisrequestisenabled,becauseWARN=INFO.logger.warn(Lowfuellevel.);//Thisrequestisdisabled,becauseDEBUGINFO.logger.debug(Startingsearchfornearestgasstation.);//Theloggerinstancebarlogger,namedcom.foo.Bar,//willinherititslevelfromtheloggernamed//com.fooThus,thefollowingrequestisenabled//becauseINFO=INFO.barlogger.info(Locatednearestgasstation.);//Thisrequestisdisabled,becauseDEBUGINFO.barlogger.debug(Exitinggasstationsearch);以一样的叁数名字调用getLogger方法,返回的reference总是指向完全相同的logger对象。例如,在这里:Loggerx=Logger.getLogger(wombat);Loggery=Logger.getLogger(wombat);x和y指向完全相同的logger对象。因此,通过这种方式可以配置一个logger,而不需要传递references就能在其他地方得到相同的
本文标题:log4j手册
链接地址:https://www.777doc.com/doc-4613086 .html