Log4net appender threshold not working

泄露秘密 提交于 2019-12-22 03:19:17

问题


I've set up a logfileAppender and a consoleAppender in my log4net config for my application. I would like the logfile appender to only write ERROR messages and above and the console appender to write DEBUG and above.

My config is:

<log4net debug="false">

<appender name="LogFileAppender" type="log4net.Appender.FileAppender,log4net" >
  <param name="File" value="log.txt" />
  <param name="AppendToFile" value="true" />
  <layout type="log4net.Layout.PatternLayout,log4net">
    <param name="ConversionPattern" value="%d %M - %m%n" />
  </layout>
  <threshold value="ERROR"/>
</appender>

<appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender"   >
  <layout type="log4net.Layout.PatternLayout">
    <param name="ConversionPattern" value="%d %m%n" />
  </layout>
</appender>


<root>
  <priority value="DEBUG" />
  <appender-ref ref="ConsoleAppender" />
  <appender-ref ref="LogFileAppender" />
</root>

</log4net>

I'm finding that both ERROR and DEBUG is being output to my logfile appender. How to restrict it to only ERROR?


回答1:


Note also that the level tag in the logger doesn't work the same way as threshold or a LevelMatchFilter.

Level indicates what log statements that actually will be generated. This is what you can test on in you code.

Threshold on the other hand, filters away all log messages that falls below your threshold.

This means that having a threshold that is higher than the highest logger level makes no sense. I have seen many times how one sets a level of INFO (because that is what most appenders will use), and then create an appender that has a threshold of DEBUG. And then you are surprised when no DEBUG messages actually appears on the appender...




回答2:


To get very specific filtering for an appender, you need to configure a LevelMatchFilter or a LevelRangeFilter for the logfile appender to filter the events which are actually output.
For example:

<filter type="log4net.Filter.LevelRangeFilter">
    <levelMin value="ERROR"/>
    <levelMax value="FATAL"/>
</filter>

or

<filter type="log4net.Filter.LevelMatchFilter">
    <levelToMatch value="ERROR"/>
</filter>

put one of these inside your <appender> tag, and this should work for you:

<appender name="LogFileAppender" type="log4net.Appender.FileAppender,log4net" >
    <filter type="log4net.Filter.LevelMatchFilter">
        <levelToMatch value="ERROR"/>
    </filter>
    <param name="File" value="log.txt" />
    <param name="AppendToFile" value="true" />
    <layout type="log4net.Layout.PatternLayout,log4net">
        <param name="ConversionPattern" value="%d %M - %m%n" />
    </layout>
    <threshold value="ERROR"/>
</appender>

Note: Updated to remove mistake pointed out by kgiannakakis.




回答3:


I've created a sample console application using your log4net config and I'm getting the exact behaviour you appear to be wanting....

using System;
using System.IO;
using log4net;
using log4net.Config;

namespace SO_1171258
{
    class Program
    {
        private static readonly ILog log = LogManager.GetLogger(typeof(Program));

        static void Main()
        {
            XmlConfigurator.ConfigureAndWatch(new FileInfo(AppDomain.CurrentDomain.GetData("APP_CONFIG_FILE").ToString()));
            log.Error(new Exception("error log statment"));
            log.Debug("debug log statment");
        }
    }
}

When I run this application, the only thing in the logfile is:

2014-01-27 15:02:51,387 Main - System.Exception: error log statment

And to the screen I see:

2014-01-27 15:05:52,190 System.Exception: error log statment

2014-01-27 15:05:52,218 debug log statment

Here is the entirety of my app.config file:

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

    <appender name="LogFileAppender" type="log4net.Appender.FileAppender,log4net" >
      <param name="File" value="log.txt" />
      <param name="AppendToFile" value="true" />
      <layout type="log4net.Layout.PatternLayout,log4net">
        <param name="ConversionPattern" value="%d %M - %m%n" />
      </layout>
      <threshold value="ERROR"/>
    </appender>

    <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender"   >
      <layout type="log4net.Layout.PatternLayout">
        <param name="ConversionPattern" value="%d %m%n" />
      </layout>
    </appender>


    <root>
      <priority value="DEBUG" />
      <appender-ref ref="ConsoleAppender" />
      <appender-ref ref="LogFileAppender" />
    </root>

  </log4net>
</configuration>



回答4:


The answers you are receiving are partly correct. The Threshold is only used to set a lower limit on the level appended. A threshold of ERROR will actually receive ERROR and FATAL (which is "above" ERROR).

You do want to implement a LevelMatchFilter with a level value of "ERROR" (and "DEBUG" for the other appender). However, you must also add a DenyAllFilter to the end of your filter chain.
For example:

<appender name="LogFileAppender" type="log4net.Appender.FileAppender,log4net" >
  <param name="File" value="log.txt" />
  <param name="AppendToFile" value="true" />
  <layout type="log4net.Layout.PatternLayout,log4net">
    <param name="ConversionPattern" value="%d %M - %m%n" />
  </layout>
  <filter type="log4net.Filter.LevelMatchFilter">
    <levelToMatch value="ERROR" />
  </filter>
  <filter type="log4net.Filter.DenyAllFilter" />
</appender>

I've had to implement the DenyAllFilter since log4net 1.2.10 (you can see the question I had on this topic here).




回答5:


You need to use additivity property. See here for an example. You need to define two loggers.



来源:https://stackoverflow.com/questions/1171258/log4net-appender-threshold-not-working

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!