在使用Serilog SelfLog时,我有一个有趣的错误。错误是:
Application: XXX.exe
Framework Version: v4.0.30319
Description: The process was terminated due to an unhandled exception.
Exception Info: System.IO.IOException
at System.IO.__Error.WinIOError(Int32, System.String)
at System.IO.FileStream.Init(System.String, System.IO.FileMode, System.IO.FileAccess, Int32, Boolean, System.IO.FileShare, Int32, System.IO.FileOptions, SECURITY_ATTRIBUTES, System.String, Boolean, Boolean, Boolean)
at System.IO.FileStream..ctor(System.String, System.IO.FileMode, System.IO.FileAccess, System.IO.FileShare, Int32, System.IO.FileOptions, System.String, Boolean, Boolean, Boolean)
at System.IO.StreamWriter.CreateFile(System.String, Boolean, Boolean)
at System.IO.StreamWriter..ctor(System.String, Boolean, System.Text.Encoding, Int32, Boolean)
at System.IO.StreamWriter..ctor(System.String, Boolean, System.Text.Encoding)
at System.IO.File.InternalAppendAllText(System.String, System.String, System.Text.Encoding)
at Serilog.Debugging.SelfLog.WriteLine(System.String, System.Object, System.Object, System.Object)
at Serilog.Sinks.PeriodicBatching.PeriodicBatchingSink+<OnTick>d__16.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(System.Threading.Tasks.Task)
at Serilog.Sinks.PeriodicBatching.PortableTimer+<OnTick>d__8.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Threading.ExecutionContext.RunInternal(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
at System.Threading.ExecutionContext.Run(System.Threading.ExecutionContext, System.Threading.ContextCallback, System.Object, Boolean)
at System.Threading.QueueUserWorkItemCallback.System.Threading.IThreadPoolWorkItem.ExecuteWorkItem()
at System.Threading.ThreadPoolWorkQueue.Dispatch()我不知道会发生什么。我有.Net Framework4.6.1,Serilog版本2.9.0,不能再次产生错误。
请你能帮我描述一下错误吗?我为什么会犯这个错误?你知道这个错误的解决方案吗?
我在下面使用图书馆:
编辑:我的应用程序在这里:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<appSettings>
<add key="serilog:minimum-level" value="Verbose" />
<add key="serilog:using:Console" value="Serilog.Sinks.Console" />
<add key="serilog:write-to:Console" />
<add key="serilog:using:Http" value="Serilog.Sinks.Http" />
<add key="serilog:write-to:Http.requestUri" value="http://log.XXX.com:8080/TestEngine" />
<add key="serilog:write-to:Http.batchPostingLimit" value="1" />
<add key="serilog:write-to:Http.batchFormatter" value="Serilog.Sinks.Http.BatchFormatters.ArrayBatchFormatter, Serilog.Sinks.Http" />
<add key="serilog:enrich:with-property:application" value="TestEngine" />
</appSettings>
<startup>
...Serilog集成在这里:
var config = new LoggerConfiguration()
.Enrich.FromLogContext()
.Enrich.WithMachineName()
.Enrich.WithUserName()
.ReadFrom.AppSettings();
if (CustomLogContext == null)
{
CustomLogContext = new Dictionary<string, object>();
}
foreach (var logContext in CustomLogContext)
{
config.Enrich.WithProperty(logContext.Key, logContext.Value);
}
if (!string.IsNullOrEmpty(CustomLogFileFullName))
{
config = config.WriteTo.File($"{CustomLogFileFullName}");
}
Serilog.Log.Logger = config.CreateLogger();
Serilog.Debugging.SelfLog.Enable(msg => File.AppendAllText("internallog.log", msg, Encoding.UTF8));
ILoggerProvider loggerProvider = new SerilogLoggerProvider(Serilog.Log.Logger);
_logger = loggerProvider.CreateLogger("XXX.Logging.Serilog");解决方案:如@RubenBartelink所述,如果使用Selflog但使用自定义日志文件,则需要承担一些风险。因为Serilog可能不会写入自定义文件,而且可能是Serilog,因此抛出IO异常。这个问题不属于Serilog。问题实际上是File.AppendAlltext操作。解决办法如下:
Serilog.Debugging.SelfLog.Enable(msg =>
{
try
{
File.AppendAllText("internallog.log", msg, Encoding.UTF8);
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
});发布于 2022-02-23 10:18:18
正如@Daniel A. White的评论中提到的那样,您正在做一件冒险的事情--尝试在“如果其他所有失败”的基础上提供的处理程序中写入文件。下面是一些例子:
SelfLog)虽然Serilog调试和诊断Wiki页面当前显示了一个写入文件的示例,但这并不是合同的本质--它绝不能失败。
因此,如果您实际上希望将SelfLog发出到文件中,则需要在处理程序中添加一个try/catch并吞下异常。
我想说,当文件库是您的主要输出时,让一个文件作为备份是非常值得怀疑的。这是双倍的情况,因为您没有任何机制来确保它被修剪(假设您有一个格式错误的消息字符串的紧循环日志记录-它最终会填充您的磁盘)。
我个人已经通过将SelfLog回显到我的Console Sink (根据上面的日志记录不会抛出)来处理这个权衡,因为可以信任操作环境(比如Kubernetes)来捕获它,或者发出警报。
https://stackoverflow.com/questions/71223500
复制相似问题