调用Flush()时,NLog是否应该刷新AsyncTargetWrapper中所有排队的消息? [英] Should NLog flush all queued messages in the AsyncTargetWrapper when Flush() is called?
问题描述
我想关闭我的应用程序并写所有未决的日志消息.因此,我在关机过程中呼叫了LogManager.Flush()
.但是,我看不到所有消息都写完了.相反,如果我等待几秒钟(使用Thread.Sleep()
),则会看到消息.
I want to shut down my application and write any pending log messages. So I call LogManager.Flush()
during my shutdown process. However, I don't see all the messages written out. Instead, if I wait for a few seconds (using Thread.Sleep()
) I see the messages.
在检查 GitHUB上的NLog代码,我发现AsyncTargetWrapper.FlushAsync()
方法仅是安排惰性写入器线程在下一批写入所有挂起的消息.它不是同步写入日志消息.
After examining NLog's code on GitHUB, I find the AsyncTargetWrapper.FlushAsync()
method is only scheduling the lazy writer thread to write all pending messages on the next batch. It is not writing log messages synchronously.
这是预期的行为吗?我期望LogManager.Flush()
是同步的,即:阻塞直到写入所有未决消息(或超过超时).
Is this the expected behaviour? I'm expecting LogManager.Flush()
to be synchronous, ie: to block until all pending messages are written (or the timeout is exceeded).
我在关机时使用的代码:
Code I use on shutdown:
LogManager.Flush(ex => { }, TimeSpan.FromSeconds(15));
然后是初始化Nlog的代码(这是Silverlight应用程序,因此我没有使用任何配置文件).
And then the code to initialise Nlog (this is a Silverlight app, so I'm not using any config files).
public static void InitialiseNLog(LogLevel forLevel)
{
var config = new LoggingConfiguration();
// Add targets.
// We need an async target wrapping a custom web service call back to the server.
var serverTarget = new RemoteServiceTarget();
var asyncWrapper = new AsyncTargetWrapper(serverTarget, 10000, AsyncTargetWrapperOverflowAction.Discard);
asyncWrapper.TimeToSleepBetweenBatches = (int)TimeSpan.FromSeconds(2).TotalMilliseconds;
asyncWrapper.BatchSize = 200;
// Add rules.
var rule = new LoggingRule("Company.Application.SilverlightApp.*", forLevel, asyncWrapper);
config.LoggingRules.Add(rule);
// Activate the configuration.
LogManager.Configuration = config;
LogManager.GlobalThreshold = forLevel;
}
推荐答案
我已经通过编辑当前的NLog源代码实现了修复程序.
I've implemented a fix by editing the current NLog source code.
在AsyncTargetWrapper.cs中,将FlushAsync()
方法从以下位置更改:
In AsyncTargetWrapper.cs, change the FlushAsync()
method from:
protected override void FlushAsync(AsyncContinuation asyncContinuation)
{
this.flushAllContinuation = asyncContinuation;
}
收件人:
protected override void FlushAsync(AsyncContinuation asyncContinuation)
{
this.flushAllContinuation = asyncContinuation;
this.ProcessPendingEvents(null); // Added to make this flush synchronous.
}
这篇关于调用Flush()时,NLog是否应该刷新AsyncTargetWrapper中所有排队的消息?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!