apache / logging-log4net

Apache Log4net is a versatile, feature-rich, efficient logging API and backend for .NET
https://logging.apache.org/log4net
Apache License 2.0
859 stars 327 forks source link

I cannot use TimeEvaluator! #149

Closed aknaldemir closed 5 months ago

aknaldemir commented 5 months ago

Hi Everyone.

I am using log4net in my .net framework 4.7.2 console project and I want to use BufferingForwardingAppender which is related ADONetAppender. When I use bufferSize and evaluator, it just run as bufferSize. Evaluator is not working.

my code is like that;

<appender name="ADONetAppender" type="log4net.Appender.ADONetAppender">
  <connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
  <connectionString value="your-connection-string" />
  <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.PatternLayout">
      <conversionPattern value="%date{yyyy-MM-dd HH:mm:ss.fff}" />
    </layout>
  </parameter>
  <!-- Diğer parametreler -->
  <bufferSize value="512" />
</appender>

<!-- BufferingForwardingAppender -->
<appender name="BufferingForwardingAppender" type="log4net.Appender.BufferingForwardingAppender">
  <!-- Buffer size büyük bir değere ayarlanmalı -->
  <bufferSize value="10000" /> <!-- 10000 gibi büyük bir buffer size değeri -->
  <lossy value="true" />
  <fix value="true" />

  <!-- TimeEvaluator kullanımı -->
  <evaluator type="log4net.Core.TimeEvaluator">
    <interval value="10" /> <!-- 10 saniyede bir logları yaz -->
  </evaluator>

  <!-- Forwarding appenders -->
  <appender-ref ref="ADONetAppender" />
  <appender-ref ref="ConsoleAppender" />
</appender>
FreeAndNil commented 5 months ago

@aknaldemir Can you please post the complete log4net config section? Did I understand correctly, that you want to buffer the log messages for 10 seconds and write them after this delay to the database?

aknaldemir commented 5 months ago

yes you understood correct. But not just 10 seconds. If buffersize is 23 then I need log again. My code is like that;

log4net.txt

FreeAndNil commented 5 months ago

I can't reproduce the problem you describe (see https://github.com/apache/logging-log4net/commit/5bc38133a0f4110c259c5800ac769be73bf125b6).

Can you try using a FileAppender instead of AdoNetAppender?

What exactly is your process? How many events do you log in which time frame?

You need to log at least one more event after the interval (10 s) to trigger a flush of the buffered events.

BTW AdoNetAppender is already a buffering appender. There is no need to insert another buffering appender.

aknaldemir commented 5 months ago

Yes I know AdoNetAppender has a buffering appender. I want like this scenario; I have a process which has 23 logs in one time. If 10 seconds are completed, it clears the buffer, and if there are 22 records in the buffer, it clears the buffer again. ` However in this case, I can see 22 logs. One log is in the buffer. Buffer ok but evaluator is not working.

`

FreeAndNil commented 5 months ago

This is not how the BufferingAppenders work. The evaluator is only evaluated when new events are logged, not when "some time passes" (because the logic calling the evaluator is unaware of its internals). When you really want such a behavior, you can flush with a timer:

  System.Threading.Timer timer = new(Flush, null, 10_000, 10_000);

static void Flush(object? _)
{
  foreach (TAppender appender in LogManager.GetRepository().GetAppenders().OfType<BufferingAppender>())
    appender.Flush();
}

Hope this helps.

FreeAndNil commented 5 months ago

Feel free to reopen in case your problem is not solved.