Log4Net RollingFileAppender没有使用低容量日志刷新IO缓冲区

Rbj*_*bjz 17 io logging log4net buffer flush

我正在考虑和HENRI COOK一样的问题.据我们从简短描述中可以看出,它被报告为Apache Jira上的一个错误.

我的问题实质上是事件只在应用程序关闭时记录(甚至在事件发生后几周).当记录量非常低时会发生这种情况.我在Windows Server 2008 R2上看到了这一点.这可以防止我们捕获并对生产错误做出反应.

现在,appender不是缓冲的.默认情况下,每次附加消息时,它还会在基础流上调用Flush().

我的问题是为什么不冲洗?除了以编程方式刷新所有appender之外,还有什么补救措施吗?你会认为一个脉动的appender是一个可行的解决方案吗?

appender配置:

<appender name="RollingErrorFileAppender" type="log4net.Appender.RollingFileAppender">
  <param name="File" value="D:\LogFiles\zzzz\xxxxxx__ERROR" />
  <param name="AppendToFile" value="true" />
  <param name="DatePattern" value="_yyyyMMddHH&quot;.log&quot;" />
  <param name="RollingStyle" value="Date" />
  <param name="StaticLogFileName" value="false" />
  <filter type="log4net.Filter.LevelRangeFilter">
    <param name="LevelMin" value="ERROR" />
    <param name="LevelMax" value="FATAL" />
  </filter>
  <layout type="log4net.Layout.PatternLayout">
    <param name="ConversionPattern" value="%utcdate{yyyy-MM-dd HH:mm:ss.fff},[%thread],%level,%logger,%m%n"/>
  </layout>
</appender>
Run Code Online (Sandbox Code Playgroud)

更新2013-06-19

我无法用任何代码重现行为.无论我尝试多么糟糕,数据总是立即写入磁盘.但是,进行了一项重要的观察:如果对文件的第一次写入大于1KiB,则修改时间永远不会随后写入更新.只有在关闭时关闭文件时才会更新它.另一方面,如果第一次写入是短的单行,则任何后续写入都将更新修改时间.这种行为在log4net和手动IO操作之间,在32位WinXP和64位W2k8R2之间,在.NET 2.0,3.5和.NET 4.0之间是一致的.这仍然没有解决问题,但至少我现在可以理解奇怪的修改时间模式.

谢谢,罗布

Ada*_*m S 29

由于您只关心错误级别或更糟糕的日志事件,并且幸运的是流量很少,我建议您将appender配置为立即刷新.

<param name="ImmediateFlush" value="true" />
Run Code Online (Sandbox Code Playgroud)

这使您无需以编程方式在每个日志事件(无论如何都不起作用)上刷新您的appender.现在,如果您希望打开更多日志级别的appender,那么当然立即刷新所有事件可能会产生更大的性能问题.

编辑

我添加了配置文件和一个用于测试的简单主程序.使用以下内容,我确实看到立即刷新日志事件.关于你的评论,我也可以ImmediateFlush从xml中删除该行,并查看默认true值是否适用于刷新.我在示例中保留了这一行,以明确说明所需的行为.

基本主要编程:

class Program
{
    static void Main(string[] args)
    {
        ILog log = LogManager.GetLogger(typeof(Program));
        XmlConfigurator.Configure(new FileInfo(@"C:\temp\logTest.config"));

        string msg;
        while ((msg = Console.ReadLine()) != "Done")
        {
            log.Error(msg);
        }

        LogManager.Shutdown();
    }
}
Run Code Online (Sandbox Code Playgroud)

main prog引用的logTest.config:

<log4net>
    <appender name="RollingErrorFileAppender" type="log4net.Appender.RollingFileAppender">
        <param name="File" value="C:\temp\log" />
        <param name="AppendToFile" value="true" />
        <param name="DatePattern" value="_yyyyMMddHH&quot;.log&quot;" />
        <param name="RollingStyle" value="Date" />
        <param name="StaticLogFileName" value="false" />
        <param name="ImmediateFlush" value="true" />
        <filter type="log4net.Filter.LevelRangeFilter">
            <param name="LevelMin" value="ERROR" />
            <param name="LevelMax" value="FATAL" />
        </filter>
        <layout type="log4net.Layout.PatternLayout">
            <param name="ConversionPattern" value="%utcdate{yyyy-MM-dd HH:mm:ss.fff},[%thread],%level,%logger,%m%n"/>
        </layout>
    </appender>
    <root>
        <level value="INFO" />
        <appender-ref ref="RollingErrorFileAppender" />
    </root>
</log4net>
Run Code Online (Sandbox Code Playgroud)

  • 解决!这是W2k8和我们的日志解析工具.W2k8带有延迟修改时间更新"功能":http://blogs.technet.com/b/asiasupp/archive/2010/12/14/file-date-modified-property-are-not-updating-while-modifying -a-file-without-closing-it.aspx我们的工具在3天后删除了日志文件检查点.总之,这造成了错误的感觉和混乱,记录被推迟了.再现的行为是在文件写入句柄关闭之前不会更新修改,除非第一次写入很小,然后在每次后续写入时更新.奇怪的功能是 (6认同)