log4net, 使用 RemotingAppender 集中管理 跨应用域(App Domain) 的 Log 信息.

........ 前言

  一个没有配备完整而强大Log功能的系统,最终会尝到苦果。

  首先尝到苦果的是系统开发维护人员,但他们有时会对此隐忍之。

  原因是,对一个已经处于运营中的项目,提出的改良,通常会被认为与风险等价。

  我现在面对的问题,就是如何在一个成熟的项目中引入Log机制,而又要将代码的改动(Risk)控制在最小范围。

........ FileAppender(FA)/RollingFileAppender(RFA) 的缺点

  Log4net 是我们在.net 系统中引入Log机制的首选,和 Log Application Block 相比, 它功能强大而不显臃肿。

FileAppender / RollingFileAppender 被广泛使用的原因在于, 本地I/O 操作和其他 Appender操作相比,代价最低。

                    FA/RFA 的缺点是没法将跨域的Log集中控制在一个文件之中。

 此话一出,一定又会被N多人鄙视+嘲讽,或许是因为我使用不当,抑或是理解不深,才得出此种错误结论。

 如果果真如此,还请各位同仁不吝指出,并权当看看 RemotingAppender 的使用吧。

........ 看 FA/RFA 的缺点

 一个Solution 中,有 A, B  两个Web Applications.

 1). 纳入 log4net.config

ContractedBlock.gif ExpandedBlockStart.gif Code
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  
<configSections>
    
<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
  
</configSections>
  
<!-- log4net -->
  
<log4net debug="true">
    
<appender name="RollingLogFileAppender" type="log4net.Appender.RollingFileAppender">
      
<file value="c:\Log\trace.txt"></file>
      
<appendToFile value="true"></appendToFile>
      
<rollingStyle value="Size"></rollingStyle>
      
<maxSizeRollBackups value="10"></maxSizeRollBackups>
      
<maximumFileSize value="10MB"></maximumFileSize>
      
<staticLogFileName value="true"></staticLogFileName>
      
<layout type="log4net.Layout.PatternLayout">
        
<conversionPattern value="%-5p %d %5rms %-22.22c{1} %-18.18M - %m%n"></conversionPattern>
      
</layout>
    
</appender>
    
    
<root>
      
<level value="DEBUG"></level>
      
<appender-ref ref="RollingLogFileAppender"></appender-ref>
    
</root>
  
</log4net>
</configuration>

 2). 修改 Global.asax.cs

protected   void  Application_Start( object  sender, EventArgs e)
ExpandedBlockStart.gifContractedBlock.gif        
{
            log4net.Config.XmlConfigurator.ConfigureAndWatch(
new FileInfo(Server.MapPath("~/log4net.config")));
        }

 

  此时,如果你将A, B 两项目中的Logfile 配置成同一个文件。

  恐怕你会苦恼于,一个项目中的Log信息OK, 另一个项目为何没能输出。

........ log4net  中的 RemotingAppender

 使用RemotingAppender, 所有项目不用更改 Global.asax.cs, 只需在log4net.config 中配置 RemotingAppender.

这不是减少了因为代码改动,而带来可能的风险吗?

ContractedBlock.gif ExpandedBlockStart.gif Code
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  
<configSections>
    
<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
  
</configSections>
  
<!-- log4net -->
  
<log4net debug="true">
    
<!--Remoting Appender-->
    
<appender name="Log4netRemotingAppender" type="log4net.Appender.RemotingAppender">
      
<param name="Sink" value="tcp://localhost:8089/Server.log4net.RemotingAppenderSink" />
      
<param name="Lossy" value="false" />
      
<param name="BufferSize" value="0" />
      
<param name="OnlyFixPartialEventData" value="true" />
    
</appender>

    
<root>
      
<level value="DEBUG"></level>
      
<appender-ref ref="Log4netRemotingAppender"></appender-ref>
    
</root>
  
</log4net>
</configuration>

 

 在启动Remoting 的地方载入:

ContractedBlock.gif ExpandedBlockStart.gif Code
ExpandedBlockStart.gifContractedBlock.gifprivate void ConfigLog4net() {

            Log4netRemotingAppender remoteAppender 
= new Log4netRemotingAppender();
            Log4netRemotingAppenderEventHandler remoteAppenderHandler 
= new Log4netRemotingAppenderEventHandler(HandleLog4netRemotingAppenderEvent);

            RemotingServices.Marshal(remoteAppender,
                    
"Server.log4net.RemotingAppenderSink",
                    
typeof(log4net.Appender.RemotingAppender.IRemoteLoggingSink));
            remoteAppender.Log4netRemoteEvent 
+= remoteAppenderHandler;

            
string strLog4netConfigurationPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "log4net.config");
            System.Console.WriteLine(
"Configurating Log4net");
            log4net.Config.XmlConfigurator.ConfigureAndWatch(
new FileInfo(strLog4netConfigurationPath));
            System.Console.WriteLine(
"Log4net configuration complete");
            logger.Debug(
"Log4net is on the fly now.");
        }


        
private void HandleLog4netRemotingAppenderEvent(object sender, Log4netRemotingAppenderEventArgs args)
ExpandedBlockStart.gifContractedBlock.gif        
{
            
//All of the log information will flow into here.
            
//thus, we can handle them in one place.
            
//
            
// Do Something with the event arguments here,
            
//Specially, check log level, then beep up contactors.
            FileInfo traceFileInfo = new FileInfo(string.Format(@"C:\Log\Trace.{0}.txt", DateTime.Now.ToString("MMddyyyy")));
            
if (!(traceFileInfo.Exists))
                File.Create(traceFileInfo.FullName).Close();

            
string strLogSourceMsg = string.Format("{0} {1} {2}",
                DateTime.Now.ToString(
"yyyy-MM-dd hh:mm:ss.fff"),
                args.LogLevel, 
                args.Context);

            
if (traceFileInfo.Exists)
ExpandedSubBlockStart.gifContractedSubBlock.gif            
{
ExpandedSubBlockStart.gifContractedSubBlock.gif                
using (StreamWriter traceWriter = new StreamWriter(traceFileInfo.FullName, true, Encoding.ASCII)){
                    traceWriter.WriteLine(
"=============== BEGIN ===============");
                    traceWriter.WriteLine(strLogSourceMsg);
                    traceWriter.WriteLine(args.LocationFullInfo);
                    traceWriter.WriteLine(args.Message);
                    traceWriter.WriteLine(
"===============  END  ===============");
                    traceWriter.Flush();
                }

            }

        }

 

 好了,开心调用 “ConfigLog4net” 吧。

........ 总结

 RemotingAppender, 不仅降低了代码的改动,更为重要的是,所有来自不同域的Log信息,全部汇入一体。

正所谓,涓涓细流,汇入大海。

 希望能为想使用RemotingAppender 的同仁提供些许帮助,就是我最大的开心了。

 祝大家工作开心!

转载于:https://www.cnblogs.com/chinaairforce1/archive/2009/07/09/1519924.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值