【问题标题】:Using 'Environment' values in log4net configuration在 log4net 配置中使用“环境”值
【发布时间】:2014-09-23 13:09:32
【问题描述】:

我的应用程序既可以作为Windows 服务 也可以在控制台环境 中启动。对于每种情况,我都需要一些 log4net 附加程序处于活动状态(或分别不处于活动状态)以及一些在两种情况下都处于活动状态的附加程序。 (服务RollingFileAppenderDebugAppender如果启用),EventLogAppender | 控制台ColoredConsoleAppenderDebugAppender如果启用))

实现类似功能的唯一方法是将PropertyFilterThreadContext.Properties 一起使用,如下所示:

<filter type="log4net.Filter.PropertyFilter">
    <key value="ApplicationMode" />
    <stringToMatch value="Service" />
</filter>

if(!Environment.UserInteractive)
    ThreadContext.Properties["ApplicationMode"] = "Service";

但是,由于该属性是在线程上下文中声明的,因此它仅适用于当前线程。如果线程更改,则配置正在重置,我必须再次声明它。

log4net 是否支持在配置中声明 PropertyFilter 以自动设置所需环境的方法?像这样:

<filter type="log4net.Filter.PropertyFilter">
    <key value="{Environment.UserInteractive}" />
    <stringToMatch value="false" />
</filter>

或者...有更好的方法吗?由于我还没有找到解决方案..这是一种不常见的做法吗?

【问题讨论】:

  • 你的控制台应用和windows服务是在两个不同的项目下吗?为什么不在每个项目中创建配置文件来满足您的需求?

标签: c# logging windows-services log4net app-config


【解决方案1】:

查看我对这个问题的回答的最后一部分:

Capture username with log4net

总而言之,您可以实现一个包含上述逻辑的对象,并将该对象放在 GlobalContext.Properties 中。当 log4net 从属性中检索值(您的对象)时,它将调用 ToString 以获取实际值。把你的逻辑放在 ToString 里面。

可能是这样的:

public class ApplicationModeProvider
{
  public override string ToString()
  {
    return Environment.UserInteractive ? "Console" : "Service";
  }
}

在启动时将其放入字典中:

GlobalContext.Properties["ApplicationMode"] = new ApplicationModeProvider();

实际上,这有点像添加

if(!Environment.UserInteractive)
    ThreadContext.Properties["ApplicationMode"] = "Service";

之前的记录语句。

我不确定,但我认为您可以按照帖子中的描述配置过滤器。

【讨论】:

  • 漂亮的解决方案! :)
猜你喜欢
  • 1970-01-01
  • 2016-04-04
  • 1970-01-01
  • 2013-05-27
  • 1970-01-01
  • 2010-12-13
  • 1970-01-01
  • 1970-01-01
  • 2014-06-02
相关资源
最近更新 更多