log4net为两个DLL命名空间配置相同的Appender。

huangapple go评论94阅读模式
英文:

log4net configure same appender for two dll namespaces

问题

我想了解如何为两个不同的命名空间配置相同的 appender。

我有:

第一个 DLL 中的 WPF.Client.Foo 类

第二个 DLL 中的 WPF.Server.Foo 类

我希望这两个类中的所有日志都可以使用相同的 appender 记录到同一个文件中。

目前,我在这两个类中都传递了相同的字符串给 ILog,但我不喜欢这样做,因为将来可能需要更改此名称或添加其他 DLL。我不能使用常量,因为每个 DLL 都是独立的,没有引用其他任何 DLL。

我不想在 Logger.config 文件中配置两个具有相同 appender 的记录器(但名称/命名空间不同),因为如果启用了日志记录,它应该始终对两个 DLL 启用,并且我不想在配置文件中更新两个阈值。

将代码合并到一个 DLL 不是选项。

我想知道是否有一种简单的方法可以配置多个完全不同且不是彼此的子命名空间的命名空间以使用相同的 appender。

谢谢。

英文:

I would like to understand how can I configure the same appender for two different namesapaces.

I have:

WPF.Client.Foo class in first dll

WPF.Server.Foo class in second dll

I want all logs in both classes to be traced with same appender to the same file.

Currently I passed the same string to the ILog in both classes but I don't like it because in the future maybe I will need to change this name or add additional dlls. I can't use a constant because every dll is independent and do not have references to any other dll.

I don't want to configure two loggers with same appender (and different name/namespase) in the Logger.config file because if the logs are enabled, it should be always enabled for both Dlls and I don't want to update two thresholds in the config file.

Merging the code to one dll is not an option.

Am I wondering if there is an easy way to configure many namespaces to same appender when the namesapaces are completely different and not a child of each other.

Thank you.

答案1

得分: 0

你可以设置一个与根记录器(root logger)关联的appender,然后让appender使用两个LoggerMatchFilter规则来进行记录器的过滤。

在下面的配置中,最后的DenyAllFilter过滤器确保任何不匹配预期记录器名称的内容不会出现在输出中。

<log4net>
  <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">

    <filter type="log4net.Filter.LevelRangeFilter">
      <levelMin value="INFO" />
      <levelMax value="FATAL" />
      <acceptOnMatch value="false" />
    </filter>

    <filter type="log4net.Filter.LoggerMatchFilter">
      <loggerToMatch value="WPF.Server.Foo" />
    </filter>
    
    <filter type="log4net.Filter.LoggerMatchFilter">
      <loggerToMatch value="WPF.Client.Foo" />
    </filter>
    
    <filter type="log4net.Filter.DenyAllFilter" />
    
    <layout type="log4net.Layout.PatternLayout">
      <conversionPattern value="%date{HH:mm:ss.ffff} Thread: [%thread] %level %logger%exception - %message%newline" />
    </layout>
  </appender>
  
  <root>
    <level value="INFO" />
    <appender-ref ref="ConsoleAppender" />
  </root>  
</log4net>
namespace WPF.Server
{
    public class Foo
    { }
}

namespace WPF.Client
{
    public class Foo
    { }
}

public class Program
{
    public static void Main()
    {
        // Logger configuration left out for brevity.
        
        var logger1 = LogManager.GetLogger(typeof(WPF.Server.Foo));
        logger1.Error("Hello from WPF.Server.Foo"); // Will appear in the log.

        var logger2 = LogManager.GetLogger(typeof(WPF.Client.Foo));
        logger2.Error("Hello from WPF.Client.Foo"); // Will appear in the log.

        var logger3 = LogManager.GetLogger("WPF.Other"); // Will not appear in the log.
        logger3.Error("Hello from other");
    }
}
英文:

You can set up an appender linked to the root logger, and let the appender do the filtering upon the loggers using two LoggerMatchFilter rules.

The last DenyAllFilter filter in below configuration ensures that anything that doesn't match the expected logger names doesn't appear in the output.

<log4net>
  <appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">

    <filter type="log4net.Filter.LevelRangeFilter">
      <levelMin value="INFO" />
      <levelMax value="FATAL" />
      <acceptOnMatch value="false" />
    </filter>

    <filter type="log4net.Filter.LoggerMatchFilter">
      <loggerToMatch value="WPF.Server.Foo" />
    </filter>
    
    <filter type="log4net.Filter.LoggerMatchFilter">
      <loggerToMatch value="WPF.Client.Foo" />
    </filter>
    
    <filter type="log4net.Filter.DenyAllFilter" />
    
    <layout type="log4net.Layout.PatternLayout">
      <conversionPattern value="%date{HH:mm:ss.ffff} Thread: [%thread] %level %logger%exception - %message%newline" />
    </layout>
  </appender>
  
  <root>
    <level value="INFO" />
    <appender-ref ref="ConsoleAppender" />
  </root>  
</log4net>
namespace WPF.Server
{
    public class Foo
    { }
}

namespace WPF.Client
{
    public class Foo
    { }
}

public class Program
{
    public static void Main()
    {
        // Logger configuration left out for brevity.
        
        var logger1 = LogManager.GetLogger(typeof(WPF.Server.Foo));
        logger1.Error("Hello from WPF.Server.Foo"); // Will appear in the log.

        var logger2 = LogManager.GetLogger(typeof(WPF.Client.Foo));
        logger2.Error("Hello from WPF.Client.Foo"); // Will appear in the log.

        var logger3 = LogManager.GetLogger("WPF.Other"); // Will not appear in the log.
        logger3.Error("Hello from other");
    }
}

huangapple
  • 本文由 发表于 2023年5月15日 02:50:47
  • 转载请务必保留本文链接:https://go.coder-hub.com/76249174.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定