F# 模块和 GetCurrentClassLogger() 的更好的 NLog 记录器名称
Better NLog logger name for F# modules and GetCurrentClassLogger()
当我在 F# 模块的顶部包含 NLog.LogManager.GetCurrentClassLogger()
时,记录器的名称类似于 <StartupCode$NLogTest>.$Program
。我希望有 NLogTest.TestModule
.
这样的东西
如何为我的 F# 模块获取更好的记录器名称?
这是一个完整的例子:
Program.fs
namespace NLogTest
type TestClass() =
let logger = NLog.LogManager.GetCurrentClassLogger()
member _.Run() =
logger.Info("Inside my class")
module TestModule =
let logger = NLog.LogManager.GetCurrentClassLogger()
let Run() =
logger.Info("Inside my module")
module Program =
[<EntryPoint>]
let Main _ =
TestClass().Run()
TestModule.Run()
0
NLogTest.fsproj
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net6.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<None Include="NLog.config">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<Compile Include="Program.fs" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="NLog" Version="4.7.13" />
</ItemGroup>
</Project>
NLog.config
<?xml version="1.0" encoding="utf-8" ?>
<nlog xmlns="http://www.nlog-project.org/schemas/NLog.xsd"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<targets>
<target name="logconsole" xsi:type="Console" />
</targets>
<rules>
<logger name="*" minlevel="Info" writeTo="logconsole" />
</rules>
</nlog>
Output
2022-02-08 18:43:52.6678|INFO|NLogTest.TestClass|Inside my class
2022-02-08 18:43:52.6997|INFO|<StartupCode$NLogTest>.$Program|Inside my module
这是我想改进的最后一行。
这里有几个选项:
在每个模块函数中创建记录器
module TestModule =
let Run() =
let logger = NLog.LogManager.GetCurrentClassLogger()
logger.Info("Inside my module")
Hard-code记录器名称
module TestModule =
let logger = NLog.LogManager.GetLogger("NLogTest.TestModule")
let Run() =
logger.Info("Inside my module")
使用nameof
运算符并使模块递归
不包括命名空间。
module rec TestModule =
let logger = NLog.LogManager.GetLogger(nameof(TestModule))
let Run() =
logger.Info("Inside my module")
创建一个 GetCurrentModuleLogger() 扩展1
似乎在很多情况下都有效,但可能更可靠。
[<AutoOpen>]
module NLogExtensions =
open NLog
type LogManager with
static member GetCurrentModuleLogger() =
let moduleFullName =
System.Diagnostics.StackTrace(1, false)
.GetFrames().[0]
.GetMethod()
.DeclaringType
.FullName
let moduleName = moduleFullName.Split("$") |> Seq.last
LogManager.GetLogger(moduleName)
1感谢 NLog.FSharp 库为我指明了这个大致方向。
当我在 F# 模块的顶部包含 NLog.LogManager.GetCurrentClassLogger()
时,记录器的名称类似于 <StartupCode$NLogTest>.$Program
。我希望有 NLogTest.TestModule
.
如何为我的 F# 模块获取更好的记录器名称?
这是一个完整的例子:
Program.fs
namespace NLogTest
type TestClass() =
let logger = NLog.LogManager.GetCurrentClassLogger()
member _.Run() =
logger.Info("Inside my class")
module TestModule =
let logger = NLog.LogManager.GetCurrentClassLogger()
let Run() =
logger.Info("Inside my module")
module Program =
[<EntryPoint>]
let Main _ =
TestClass().Run()
TestModule.Run()
0
NLogTest.fsproj
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net6.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<None Include="NLog.config">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
<Compile Include="Program.fs" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="NLog" Version="4.7.13" />
</ItemGroup>
</Project>
NLog.config
<?xml version="1.0" encoding="utf-8" ?>
<nlog xmlns="http://www.nlog-project.org/schemas/NLog.xsd"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<targets>
<target name="logconsole" xsi:type="Console" />
</targets>
<rules>
<logger name="*" minlevel="Info" writeTo="logconsole" />
</rules>
</nlog>
Output
2022-02-08 18:43:52.6678|INFO|NLogTest.TestClass|Inside my class
2022-02-08 18:43:52.6997|INFO|<StartupCode$NLogTest>.$Program|Inside my module
这是我想改进的最后一行。
这里有几个选项:
在每个模块函数中创建记录器
module TestModule =
let Run() =
let logger = NLog.LogManager.GetCurrentClassLogger()
logger.Info("Inside my module")
Hard-code记录器名称
module TestModule =
let logger = NLog.LogManager.GetLogger("NLogTest.TestModule")
let Run() =
logger.Info("Inside my module")
使用nameof
运算符并使模块递归
不包括命名空间。
module rec TestModule =
let logger = NLog.LogManager.GetLogger(nameof(TestModule))
let Run() =
logger.Info("Inside my module")
创建一个 GetCurrentModuleLogger() 扩展1
似乎在很多情况下都有效,但可能更可靠。
[<AutoOpen>]
module NLogExtensions =
open NLog
type LogManager with
static member GetCurrentModuleLogger() =
let moduleFullName =
System.Diagnostics.StackTrace(1, false)
.GetFrames().[0]
.GetMethod()
.DeclaringType
.FullName
let moduleName = moduleFullName.Split("$") |> Seq.last
LogManager.GetLogger(moduleName)
1感谢 NLog.FSharp 库为我指明了这个大致方向。