我的主应用程序可以在控制台环境中启动,也可以作为 Windows服务启动,基于某些指标(启动标记,#if指令,......)。只要应用程序在“生产模式”中运行,例如如果没有用户上下文作为启动服务,我想将其记录在文件(信息,警告)以及 Windows事件日志中。但是,当我正在调试时,我希望只将日志消息传送到控制台窗口。
有没有办法使用log4net实现这一点,不包括在运行时触摸应用程序配置?
答案 0 :(得分:3)
坦率地说,代码方法对我来说听起来不是一个好主意,因为它隐藏了最终会管理系统的人的某些行为。既然你可能有两个构建配置(发布和调试?),为什么不用它们代替你正在做的change the configuration file depending on the build。
如果你真的不想这样做,那么这里是如何做到的:你可以在你的log4net库的全局上下文中设置一个自定义属性
// declare this code as soon as you've determined what context you're in
log4net.GlobalContext.Properties["ApplicationMode"] = "Service";
// or 'Console", with an #IF directive
然后在您的log4net配置中,您可以使用log {4}的PropertyFilter
过滤掉您的appender将捕获的消息
你的开发者的控制台appender:
<appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender,log4net">
<filter type="log4net.Filter.PropertyFilter">
<key value="ApplicationMode" />
<stringToMatch value="Console" />
<acceptOnMatch value="true" />
</filter>
<filter type="log4net.Filter.DenyAllFilter" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %-5level %-25.25logger{1} - %message%newline" />
</layout>
</appender>
和您的作品的文件追加器
<appender name="FileAppender" type="log4net.Appender.FileAppender,log4net">
<filter type="log4net.Filter.PropertyFilter">
<key value="ApplicationMode" />
<stringToMatch value="Service" />
<acceptOnMatch value="true" />
</filter>
<filter type="log4net.Filter.DenyAllFilter" />
<file value="mylogfile.txt" />
<appendToFile value="true" />
<lockingModel type="log4net.Appender.FileAppender+MinimalLock" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date %-5level %-25.25logger{1} - %message%newline" />
</layout>
</appender>
然后为您的日志声明所有appender:
<root>
<level value="DEBUG"/>
<appender-ref ref="FileAppender"/>
<appender-ref ref="ConsoleAppender"/>
</root>
这将根据全局属性中的值将您的消息分派给正确的appender。 DenyAllFilter
很重要; log4net的工作原理是默认情况下允许所有邮件通过,而您只希望邮件与PropertyFilter
答案 1 :(得分:0)
可以以编程方式创建,修改或删除所有appender。为什么不删除你想要避免的appender?这允许您使用相同的代码来检测您正在调试和/或在控制台中运行。
以编程方式禁用appender:
log4net.Appender.IAppender[] appenders = log4net.LogManager.GetRepository().GetAppenders();
for (int i = 0; i < appenders.Length; ++i)
{
Log4net.Appender.FileAppender appender = appenders[i] as log4net.Appender.FileAppender;
if (appender != null && appender.Name == "RollingFile")
appender.Threshold = log4net.Core.Level.Off;
}