c# - Serilog JSON 配置中的 "Using"有什么作用?

标签 c# .net-core serilog

Using 在 Serilog JSON 配置(例如在 .Net Core 环境中的 AppSettings.json 文件中)实际上做了什么?

让我们以这个配置为例:

"Serilog": {
  "Using": [ "Serilog.Sinks.Console" ], <=======***HERE***=========
  "MinimumLevel": "Debug",
  "WriteTo": [
    { "Name": "Console" },
    {
      "Name": "RollingFile",
      "Args": {
        "pathFormat": "logs\\log-{Date}.txt",
        "outputTemplate": "{Timestamp:yyyy-MM-dd HH:mm:ss.fff zzz} [{Level}] {Message}{NewLine}{Exception}"
      }
    }
  ],
  "Enrich": [ "FromLogContext", "WithMachineName", "WithThreadId" ],
  "Properties": {
    "Application": "My Application"
  }
}

在上面的例子中,我们使用了 File sink 而没有 将它添加到 Using 属性。但是,一切似乎都正常。

所以我不明白为什么我们基本上需要这个 Using 。有人可以向我解释一下吗?

最佳答案

这在 Serilog.Settings.Configuration 的文档中有介绍:

(This package implements a convention using DependencyContext to find any package with Serilog anywhere in the name and pulls configuration methods from it, so the Using example above is redundant.)



这意味着它用于定义用于定位 Serilog sinks 的包,但是在使用 Serilog.Settings.Configuration 包时它是多余的。

更多信息

我查看了 Serilog 源代码,以便能够提供更多关于 Using 究竟做了什么以及为什么首先需要它的信息。我希望下面的解释有帮助。

考虑以下基于代码的设置:
Log.Logger = new LoggerConfiguration()
    .WriteTo.Console()
    .CreateLogger();

在这个例子中, ConsoleLoggerSinkConfiguration 的扩展方法(因此它的第一个参数是 LoggerSinkConfiguration 的一个实例)。使用这种基于代码的方法时,只有在引用的程序集中可以找到此扩展方法时,代码才会编译。

接下来,考虑以下方法,它使用基于 IConfiguration 的方法:
Log.Logger = new LoggerConfiguration()
    .ReadFrom.Configuration(someConfiguration)
    .CreateLogger();

{
    "Serilog": {
        "Using": ["Serilog.Sinks.Console"], // Redundant.
        "WriteTo": ["Console"]
    }
}

在这个例子中,编译过程不知道 JSON 字符串值 "Console" 指的是什么,因此需要一个可以从字符串 "Console" 到上述 Console() 扩展方法的过程。为此,Serilog 需要首先在运行时找到扩展方法(在本例中,它位于 Serilog.Sinks.Console 程序集中)。

这个查找过程是使用反射完成的,它对 find public static methods that take as their first parameter a LoggerSinkConfiguration 进行了一些汇编扫描。在查找这些扩展方法时,您在问题中询问的 Using 指令是 mechanism for helping determine exactly which assemblies should be scanned

正如文档所述,基于 IConfiguration 的方法使用 DependencyContextautomatically scan assemblies that have Serilog in their name 。由于 Serilog.Sinks.Console 的名称中确实包含 Serilog,因此无需将其添加到 Using 指令中。使用此方法时,您还可以选择 provide your own DependencyContext instance,因此您可能需要明确说明在查找接收器时要扫描哪些程序集。

关于c# - Serilog JSON 配置中的 "Using"有什么作用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53796152/

相关文章:

C# 串行日志 : how to log with String interpolation and keep argument names in message templates?

logging - Serilog - 如何为文件接收器自定义解构类对象的输出格式

javascript - 如何在动态链接函数jquery函数C#上传递多个参数?

c# - Visual Studio Intellisense 不显示某些类

asp.net-core - 使用具有目标框架名称(如 #if !NETSTANDARD1_6)的代码编译 netcoreapp1.0

c# - 多个 AddHostedService dotnet 核心

c# - ILogger 不使用 Serilog 写入控制台

c#存储库模式 : One repository per subclass?

c# - PayPal 沙盒执行调用返回错误 400 错误请求

c# - Process.Start 在 MAC OS 中使用 .NET 核心给出错误 - 没有这样的文件或目录