.NET开源项目介绍及资源推荐:日志记录

在项目开发中,日志记录是任何时候都少不了的,在本文中,将简单介绍一下如下几种日志记录工具,以及推荐一些学习的资源:

1Log4net

2Logging Application Block

3NLog

 

一.Log4net

Log4net是从java平台下非常优秀的日志记录框架log4j上移植到.NET下的,它是apache基金资助的项目的一部分。Log4net可以帮助我们把日志信息输出到各种不同目标(文本文件、数据库、控制台等)的.net类库,它可以容易的加载到开发项目中,实现程序调试和运行的时候的日志信息输出,提供了比.net自己提供的debug类和trace类的功能更多,使用起来也是非常的简单。在Log4net 主要有四种重要的组件,分别是Logge, Repository, Appender以及 LayoutLog4net支持两种不同的配置方式:配置文件和代码配置,一般情况下推荐使用配置文件,一个完整的配置示例如下:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  
<configSections>
    
<section name="log4net" 
      type
="log4net.Config.Log4NetConfigurationSectionHandler, 
            log4net-net-1.0"
 />
  
</configSections>

  
<log4net>

    
<root>
      
<level value="WARN" />
      
<appender-ref ref="AdoNetAppender" />
      
<appender-ref ref="ConsoleAppender" />
    
</root>

    
<logger name="testApp.Logging">
      
<level value="DEBUG"/>
    
</logger>

    
<appender name="AdoNetAppender" type="log4net.Appender.AdoNetAppender">
      
<bufferSize value="100" />
      
<connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
      
<connectionString value="data source=[database server];initial catalog=[database name];integrated security=false;persist security info=True;User ID=[user];Password=[password]" />
      
<commandText value="INSERT INTO Log ([Date],[Thread],[Level],[Logger],[Message],[Exception]) VALUES (@log_date, @thread, @log_level, @logger, @message, @exception)" />
      
<parameter>
        
<parameterName value="@log_date" />
        
<dbType value="DateTime" />
        
<layout type="log4net.Layout.RawTimeStampLayout" />
      
</parameter>
      
<parameter>
        
<parameterName value="@thread" />
        
<dbType value="String" />
        
<size value="255" />
        
<layout type="log4net.Layout.PatternLayout">
          
<conversionPattern value="%thread" />
        
</layout>
      
</parameter>
      
<parameter>
        
<parameterName value="@log_level" />
        
<dbType value="String" />
        
<size value="50" />
        
<layout type="log4net.Layout.PatternLayout">
          
<conversionPattern value="%level" />
        
</layout>
      
</parameter>
      
<parameter>
        
<parameterName value="@logger" />
        
<dbType value="String" />
        
<size value="255" />
        
<layout type="log4net.Layout.PatternLayout">
          
<conversionPattern value="%logger" />
        
</layout>
      
</parameter>
      
<parameter>
        
<parameterName value="@message" />
        
<dbType value="String" />
        
<size value="4000" />
        
<layout type="log4net.Layout.PatternLayout">
          
<conversionPattern value="%message" />
        
</layout>
      
</parameter>
      
<parameter>
        
<parameterName value="@exception" />
        
<dbType value="String" />
        
<size value="2000" />
        
<layout type="log4net.Layout.ExceptionLayout" />
      
</parameter>
    
</appender>

    
<appender name="ConsoleAppender" 
              type
="log4net.Appender.ConsoleAppender" >
      
<layout type="log4net.Layout.PatternLayout">
        
<param name="ConversionPattern" 
           value
="%d [%t] %-5p %c [%x] - %m%n" 
        
/>
      
</layout>
    
</appender>

  
</log4net>
</configuration>

在该示例中,配置了两种目标的输出,分别为数据库和控制台方式,在代码中使用示例:

Log4net.ILog log = Log4net.LogManager.GetLogger("MyLogger"); 

if (log.IsDebugEnabled)
    log.Debug(
"message"); 

if (log.IsInfoEnabled)
   log.Info(
"message");

Log4net已经能够完全满足我们日常开发的日志记录功能,但是它容易为人所诟病的一点是没有可视化的配置工具支持,需要手工编写配置文件。如果你还在担心这一点,不妨看看这篇《Log4net GUI configuration tool》文章,文中作者为我们提供了一种Log4net的可视化配置工具,界面如下所示:

官方主页:http://logging.apache.org/log4net/

学习资料

1Log4net官方文档

2Sema翻译的Log4net使用指南 (个人认为,如果你从没有接触过Log4net,看这篇就足够使用它了)

3.菩提树的Log4net五步走也很值得推荐。

 

二.Logging Application Block

Logging Application Block是微软Enterprise Library其中的一个应用程序块,可以使开发人员可以在其应用程序中集成标准的日志和监测功能,应用程序可以使用日志和监测块在多个位置记录事件,记录的位置包括:事件日志(Event Log)、电子邮件(Email)、数据库(DataBase)、文本文件(TextFile)、消息队列(MSMQ)、WMI、用户自定义位置。并且使用Enterprise Library Configuration工具进行完全可视化配置,并且可以设置输出日志信息的格式。如图所示:

配置完成后,所有的配置都放在了应用程序配置文件里面(针对EL2.0):

<configuration>
  
<configSections>
    
<section name="loggingConfiguration" type="Microsoft.Practices.EnterpriseLibrary.Logging.Configuration.LoggingSettings, Microsoft.Practices.EnterpriseLibrary.Logging" />
  
</configSections>
  
<loggingConfiguration tracingEnabled="true" defaultCategory="General">
    
<logFilters>
      
<add
          
name="Category"
          type
="Microsoft.Practices.EnterpriseLibrary.Logging.Filters.CategoryFilter, Microsoft.Practices.EnterpriseLibrary.Logging"
          categoryFilterMode
="AllowAllExceptDenied">
        
<categoryFilters>
          
<add name="UI Events" />
        
</categoryFilters>
      
</add>
      
<add
          
name="Priority"
          type
="Microsoft.Practices.EnterpriseLibrary.Logging.Filters.PriorityFilter, Microsoft.Practices.EnterpriseLibrary.Logging"
          minimumPriority
="2"
                    
/>
      
<add name="LogEnabled Filter"
        type
="Microsoft.Practices.EnterpriseLibrary.Logging.Filters.LogEnabledFilter, Microsoft.Practices.EnterpriseLibrary.Logging, Version=2.0.0.0, Culture=neutral, PublicKeyToken=null"
        enabled
="true" 
           
/>
    
</logFilters>
  
</loggingConfiguration>
</configuration>

在代码中使用时非常简单,如下代码片断所示:

LogEntry logEntry = new LogEntry();

logEntry.EventId 
= 100;

logEntry.Priority 
= 2;

logEntry.Message 
= "Informational message";

//设置多个Category

logEntry.Categories.Add(
"Trace");

logEntry.Categories.Add(
"UI Events");


Logger.Write(logEntry);

很多朋友使用Logging Application Block,有一个担心的地方就是Enterprise Library 2.0中把所有的配置信息都放在了应用程序配置文件里面,这样由配置工具生成的配置代码和我们手工添加的一些配置代码混合在一起,会显得非常混乱,如果你有这样的疑问,想把每一个应用程序块的配置信息单独放在外部文件中,不妨看看这篇文章《Enterprise Library 2.0 技巧(1):如何使用外部配置文件

关于Logging Application Block还应该提一下它的可扩展性,除了系统中默认的输出目标之外,用户可以自行扩展自己的目标,比如说控制台等;除此之外,用户也可以扩展自己的日志输出格式,比如说XML格式等。

官方主页:http://msdn.microsoft.com/practices/

学习资源

1Enterprise Library Step By Step系列(七):日志和监测应用程序块——入门篇

2Enterprise Library Step By Step系列(八):日志和监测应用程序块——进阶篇

3Enterprise Library 2.0(2):Logging Application Block学习

4Enterprise Library 2.0 技巧(3):记录ASP.NET站点中未处理的异常

5Enterprise Library 2.0 技巧(4):如何用编程的方法来配置Logging Application Block

6Enterprise Library 2.0 Hands On Lab 翻译(4):日志应用程序块(一)

7Enterprise Library 2.0 Hands On Lab 翻译(5):日志应用程序块(二)

8Enterprise Library 2.0 Hands On Lab 翻译(6):日志应用程序块(三)

 

三.NLog

NLogC#编写的开源日志类库,它的设计思想是使其简单而灵活。NLog让你处理诊断的日志消息,用相关信息扩充消息,依照你的选择格式化日志消息和把日志消息输出到一个或多个目的地,基本上类似于Log4net。同样,NLog也提供了很多的扩展,可以自定义日志输出目标,日志格式,过滤器等。看一个简单的配置示例:

<nlog xmlns="http://www.nlog-project.org/schemas/NLog.xsd" 
      xmlns:xsi
="http://www.w3.org/2001/XMLSchema-instance">
  
<targets>
    
<target name="console" xsi:type="ColoredConsole" 
            layout
="${date:format=HH\:mm\:ss}|${level}|${stacktrace}|${message}"/>
    
<target name="file" xsi:type="File" fileName="${basedir}/file.txt" 
            layout
="${stacktrace} ${message}"/>
  
</targets>
  
<rules>
    
<logger name="*" minlevel="Trace" writeTo="console,file"/>
  
</rules>
</nlog>

在代码中使用如下所示:

static void C() 

    logger.Info(
"Info CCC"); 
}
 

static void B() 

    logger.Trace(
"Trace BBB"); 
    logger.Debug(
"Debug BBB"); 
    logger.Info(
"Info BBB"); 

    C(); 

    logger.Warn(
"Warn BBB"); 
    logger.Error(
"Error BBB"); 
    logger.Fatal(
"Fatal BBB"); 
}
 

static void A() 

    logger.Trace(
"Trace AAA"); 
    logger.Debug(
"Debug AAA"); 
    logger.Info(
"Info AAA"); 

    B(); 

    logger.Warn(
"Warn AAA"); 
    logger.Error(
"Error AAA"); 
    logger.Fatal(
"Fatal AAA"); 
}
 

static void Main(string[] args) 

    logger.Trace(
"This is a Trace message"); 
    logger.Debug(
"This is a Debug message"); 
    logger.Info(
"This is an Info message"); 

    A(); 

    logger.Warn(
"This is a Warn message"); 
    logger.Error(
"This is an Error message"); 
    logger.Fatal(
"This is a Fatal error message"); 

}

NLog虽然没有提供可视化的配置工具,但是安装后,我们会在VS2005New Item里面看到有关本NLog的配置文件这么一项,是用该配置文件是支持自动补全功能的。

官方主页:http://www.nlog-project.org/

学习资源

没有发现目前有好的中文学习资源,大家可以参考官方文档,希望有时间可以写几篇NLog的使用教程,弥补一下当前中文文档的空缺。

 

总结

以上简单的介绍了.NET下的几种开源日志记录框架,如果你的系统整体架构都使用了Enterprise Library,那么使用Logging Application Block更适合你;否则,如果使用了NHiberante或者Castle等数据持久框架,那么选用Log4net将会更适合,因为在NH中本身就是用Log4net作为日志记录工具的;在没有使用任何其他框架的情况下,可以在以上几种工具中自行选用,个人认为它们都很优秀!

作者:TerryLee
出处:http://terrylee.cnblogs.com
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
posted @ 2006-12-03 23:28 TerryLee 阅读(13620) 评论(40)  编辑 收藏 所属分类: Open Source

  回复  引用  查看    
#1楼 2006-12-04 01:43 | 木野狐      
:)
  回复  引用  查看    
#2楼 [楼主]2006-12-04 08:17 | TerryLee      
@木野狐
:)
  回复  引用  查看    
#3楼 2006-12-04 08:33 | Tseng      
总结得不错,在认识上面几个项目之前,我都是自己写CATCH异常的。
  回复  引用  查看    
#4楼 [楼主]2006-12-04 08:36 | TerryLee      
@Tseng
对于异常信息,使用日志记录组件记录是非常必要的:)
  回复  引用    
#5楼 2006-12-04 08:58 | jjx [未注册用户]
spring.net 开发团队现在已经开发了一个类似apache commons logging的项目,Common.Logging
  回复  引用  查看    
#6楼 [楼主]2006-12-04 09:25 | TerryLee      
@jjx
没用过,不知道好不好使呢?
  回复  引用  查看    
#7楼 2006-12-04 09:29 | 壮志      
谢谢介绍,准备使用Logging Application Block了。
  回复  引用  查看    
#8楼 2006-12-04 09:30 | Ariel Y.      
你说的那个“自动补全功能”官方说法是不是叫“智能感知”啊,呵呵。
  回复  引用    
#9楼 2006-12-04 10:26 | jjx [未注册用户]
@TerryLee

http://bbs.dotnettools.org/NewsDetail.asp?id=5760



目前有许多日志的实现,像log4net,nlog,logging application block,避免对某一实现的依赖就是common logging所要做的事情。

common logging 提供简单的日志实现,目前提供的是无输出,控制台,Trace(以上三种实现,在配置文件factoryAdapter type attribute中有简写方式NOOP,CLOSE,TRACE. 简单的配置如下



<configuration>
<configSections>
<sectionGroup name="common">
<section name="logging" type="Common.Logging.ConfigurationSectionHandler, Common.Logging" />
</sectionGroup>
</configSections>
<common>
<logging>
<factoryAdapter type="Common.Logging.Simple.ConsoleOutLoggerFactoryAdapter, Common.Logging">
<arg key="showLogName" value="true" />
<arg key="showDataTime" value="true" />
<arg key="level" value="ALL" />
<arg key="dateTimeFormat" value="yyyy/MM/dd HH:mm:ss:fff" />
</factoryAdapter>
</logging>
</common>
</configuration>




上面的配置使用控制台输出,并设置showLogName showDateTime,level为ALL,dateTimeFormat为yyyy/MM/dd(不同的实现有不同的参数设定)


但是common logging 的主要任务并不是提供一个日志功能,它的主要作用正如ILoggerFactoryAdapter名字描述的一样,提供一个日志的工厂的适配器,以便你方便的切换到其它的日志实现


切换到log4net实现

<sectionGroup name="common">
<section name="logging" type="Common.Logging.ConfigurationSectionHandler, Common.Logging" />
</sectionGroup>

<common>
<logging>
<factoryAdapter type="Common.Logging.Log4Net.Log4NetLoggerFactoryAdapter, Common.Logging.Log4Net">
<!-- configType可选 INLINE, FILE, FILE-WATCH, EXTERNAL-->
<<arg key="configType" value="INLINE" />
</factoryAdapter>
</logging>
</common>



上面的configType是INLINE,就是使用log4net原来的在app.config/web.config中的配置方式。


这里的实现有个简单的好处是你不必要调用XmlConfigurator.Configure()因为Log4NetLoggerFactoryAdapter给你做了这些

Log4NetLoggerFactoryAdapter的部分代码

switch ( configType )
{
case "INLINE":
XmlConfigurator.Configure();
break;
case "FILE":
XmlConfigurator.Configure( new FileInfo( configFile ) );
break;
case "FILE-WATCH":
XmlConfigurator.ConfigureAndWatch( new FileInfo( configFile ) );
break;
case "EXTERNAL":
// Log4net will be configured outside of Common.Logging
break;
default:
BasicConfigurator.Configure();
break;
}



  回复  引用  查看    
#10楼 [楼主]2006-12-04 10:39 | TerryLee      
@壮志

  回复  引用  查看    
#11楼 [楼主]2006-12-04 10:39 | TerryLee      
@Ariel Y.
没错,也有人叫“自动补全”
  回复  引用  查看    
#12楼 [楼主]2006-12-04 10:42 | TerryLee      
@jjx
在实际开发中,关于日志记录,记录到数据库的方式最为常见

如果common logging不提供对Database的输出,估计不会在项目中使用:)
  回复  引用    
#13楼 2006-12-04 10:45 | jjx [未注册用户]
@TerryLee

上面说了,common logging并不是以提供日志功能为主的,它是为了解决对特定日志的依赖。你可以使用其它实现提供的数据库日志
  回复  引用  查看    
#14楼 2006-12-04 10:46 | 高海东      
日志我刚好用上
  回复  引用    
#15楼 2006-12-04 12:29 | Marmot[匿名] [未注册用户]
谢谢!希望能看到更多的其他方面的介绍:-)
支持!
  回复  引用    
#16楼 2006-12-04 16:07 | 580k [未注册用户]
使用580k.com帮您关注此blog更新
580k是一种WEB形式的网页监控工具(网址:http://***/).所谓网页监控工具,用其首页的描述,就是:您关注的网页内容发生变化时,580k会将变化的内容用邮件通知您.
580K作为WEB工具,其提供的功能是有实际应用的,相信一些需要每天关注大量信息的人,如公司老总、炒股者、网络编辑、情报员、论坛灌水爱好者、新闻评论员等,会非常喜欢使用它的.
  回复  引用  查看    
#17楼 [楼主]2006-12-04 18:33 | TerryLee      
@高海东
希望我的介绍对大家有所帮助:)
  回复  引用  查看    
#18楼 [楼主]2006-12-04 18:35 | TerryLee      
@Marmot[匿名]
前面介绍了IOC容器、数据持久层,后续还有几篇吧:)
  回复  引用    
#19楼 2006-12-06 12:43 | Bruse[匿名] [未注册用户]
请问Logging Application Block能把日志直接记录到Access数据库中去吗,谢谢!
  回复  引用  查看    
#20楼 [楼主]2006-12-06 13:00 | TerryLee      
@Bruse[匿名]
应该是不行,需要自己写相关的Provider
  回复  引用    
#21楼 2006-12-07 01:11 | Efly [未注册用户]
TerryLee
看了后,我式了下,不是很明白作用,照着例子我做了一个Log4net的
可以输出信息到文本中。但是个人不知道实际中到底是怎么用的·
就像
if (log.IsDebugEnabled)
log.Debug("message");
这,输出message 这个东西是我们人写的,有什么用呢?另外,这个东西大概就是应用程序出现异常的时候将信息写入,。那么我怎么知道程序在运行中哪里会出现异常?也就是说,要在程序中写类似log.Debug("message");这样才会输出信息,那我在设计的时候可能很多地方不都要加这语句?
感觉是不是和 try catch一起用的。然后将 catch到的Exception
用log.Debug(e.Tostring());写入 文本中?
怒我较笨,不是很理解 这个的作用~~~才刚刚开始接触这东西·实际中具体是怎么用的?楼主能否对小弟开导一下?万分感谢~!!!
  回复  引用  查看    
#22楼 2006-12-14 15:32 | Anthan      
Log4net是完全开源的嘛?
我按照你所讲的做了个例子,可是记录不到日志到数据库中啊?
连接字符串已经改了,难道要在数据库中建相应的log表嘛?
  回复  引用  查看    
#23楼 [楼主]2006-12-15 00:00 | TerryLee      
@Efly
很多种情况,try-catch可以使用,在Web项目中,Application_Error中也可以使用
  回复  引用  查看    
#24楼 [楼主]2006-12-15 00:00 | TerryLee      
@Anthan
是完全开源的

在数据库当然需要有相应的Log表了
  回复  引用  查看    
#25楼 2006-12-15 16:26 | Anthan      
NLog的配置文件在Web程序中有特别的地方吗?
我配的好像不好使噢。
<targets>
<target xsi:type="File" name="file" fileName="../../Logfile/logfile.txt"
layout="${date:format=yyyy/MM/dd-HH\:mm\:ss}|${level}|${stacktrace}|${message}"/>
</targets>
<rules>
<logger name="*" minlevel="Trace" writeTo="file"/>
</rules>


  回复  引用  查看    
#26楼 [楼主]2006-12-15 21:10 | TerryLee      
@Anthan
没有具有用过啊
  回复  引用    
#27楼 2007-04-05 11:46 | Michael zhang [未注册用户]
借宝地问问,ORM类似的对象持久化设计,,,你们是怎么处理报表的,比如导出Excel,其它报表等等.因为就我知道的,水晶报表和Dataset操作比较好
  回复  引用    
#28楼 2007-09-21 09:29 | taylor [未注册用户]
顶!谢谢楼主,超赞一个!

标题  
姓名  
主页
Email (博主才能看到)