我正在为Serilog编写一个增强器,我希望在实践中添加一个可能触发新日志事件的属性:
public void Enrich(LogEvent logEvent, ILogEventPropertyFactory propertyFactory)
{
ISession session = /* HttpContext.Session */;
logEvent.AddPropertyIfAbsent(propertyFactory.CreateProperty("ValueFromSession", session.GetString("ValueFromSession")));
/* other properties ... */
}
我希望能够将我的http会话中的值添加到我的日志中,因此我将LogContext.PushProperties
与自定义Richher一起使用。 ASP.NET Core会在读取过期会话时记录警告,这会触发我的richher,但每当我尝试从richver中的会话中读取时,它会向我发出关于过期会话的警告,这会触发我的richr的新实例(ad infitum) )。这导致StackOverflowException
似乎无法通过try
块进行捕获。
在Enrich
方法中,有没有办法禁用日志记录?或者我可以以某种方式检测这种递归(除了解析堆栈跟踪)?
答案 0 :(得分:0)
我的自定义ILogger
实现(不使用Serilog)遇到了这个问题。它会在访问Session对象时发生。我设法通过在启动时将持久密钥的DataProtection添加到我的应用程序来解决这个问题。
services.AddDataProtection()
.PersistKeysToFileSystem(new DirectoryInfo("keys"));
我没有深入了解实现细节,但是从我在DistributedSession代码中看到的情况,当检测到旧的会话密钥时,会记录“访问过期的会话”消息。这里的问题是日志记录发生在isAvailable
标志设置为true
之前,这会导致递归。我不知道为什么添加DataProtection可以避免这个问题,但是DataProtection可能导致_isNewSessionKey
总是true
。
GitHub中建议的另一种解决方法是添加中间件以保存要记录到HttpContext.Items的会话项。然后在记录器中检索这些项目。