【问题标题】:Identity-layout-renderer is not rendering anything for .NET Core console ApplicationIdentity-layout-renderer 没有为 .NET Core 控制台应用程序渲染任何内容
【发布时间】:2020-02-21 08:21:38
【问题描述】:

我有一个 .NET Core 控制台应用程序。

像这样:

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFrameworks>netcoreapp2.1;netcoreapp3.1</TargetFrameworks>
  </PropertyGroup>

我在带有 VS 2019 的 Windows 10 上运行。

我无法让下面的布局渲染器记录任何内容。

https://github.com/NLog/NLog/wiki/Identity-layout-renderer

${identity:authType=Boolean:separator=String:name=Boolean
          :isAuthenticated=Boolean}

我的 nlog.config

<?xml version="1.0" encoding="utf-8" ?>
<!-- XSD manual extracted from package NLog.Schema: https://www.nuget.org/packages/NLog.Schema-->
<nlog xmlns="http://www.nlog-project.org/schemas/NLog.xsd" xsi:schemaLocation="NLog NLog.xsd"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      autoReload="true"
      internalLogFile="MyApp.NLog.INTERNAL.log"
      internalLogLevel="Info" >

  <!-- the targets to write to -->
  <targets>
    <!-- write logs to file -->
    <target xsi:type="File" name="target1" fileName="MyApp.NLog.${shortdate}.log"
            layout="${date}|${level:uppercase=true}|${logger}|***|${identity:authType=true:separator=/:name=true:isAuthenticated=true}|****|${message} ${exception:format=toString,Data}|${all-event-properties}" />

  </targets>



  <!-- rules to map from logger name to target -->
  <rules>
    <logger name="*" minlevel="Trace" writeTo="target1" />
  </rules>
</nlog>

示例日志::(

2020/02/19 12:03:40.617|INFO|MyCompany.MyObject|***||****|HeyYouThere |

***||**** 之间没有任何关系:(

和nlog内部日志输出(MyApp.NLog.INTERNAL.log)(没有错误)

2020-02-19 12:03:38.3612 Info Auto loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.Extensions.Logging.dll
2020-02-19 12:03:38.3734 Info Loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.Extensions.Logging.dll
2020-02-19 12:03:38.3847 Info NLog.Extensions.Logging, Version=1.0.0.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c. File version: 1.6.1.1203. Product version: 1.6.1.
2020-02-19 12:03:38.3847 Info Auto loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.Extensions.Logging.dll succeeded!
2020-02-19 12:03:38.3847 Info Auto loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.WindowsIdentity.dll
2020-02-19 12:03:38.3847 Info Loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.WindowsIdentity.dll
2020-02-19 12:03:38.3938 Info NLog.WindowsIdentity, Version=4.0.0.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c. File version: 4.6.8.10751. Product version: 4.6.8.
2020-02-19 12:03:38.3938 Info Auto loading assembly file: c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\NLog.WindowsIdentity.dll succeeded!
2020-02-19 12:03:38.3938 Info Message Template Auto Format enabled
2020-02-19 12:03:38.4652 Info Adding target FileTarget(Name=target1)
2020-02-19 12:03:38.5111 Info Found 39 configuration items
2020-02-19 12:03:38.5614 Info Configuration file change detected! Reloading in 1000ms...
2020-02-19 12:03:38.5614 Info Configuration file change detected! Reloading in 1000ms...
2020-02-19 12:03:39.5688 Info Reloading configuration...
2020-02-19 12:03:39.5688 Info Configuring from an XML element in c:\myfolder1\myfolder2\bin\Debug\netcoreapp3.1\nlog.config...
2020-02-19 12:03:39.5688 Info Message Template Auto Format enabled
2020-02-19 12:03:39.5688 Info Adding target FileTarget(Name=target1)
2020-02-19 12:03:39.5688 Info Closing old configuration.
2020-02-19 12:03:39.5987 Info Found 39 configuration items

Nuget 包

  <ItemGroup>
    <PackageReference Include="NLog" Version="4.6.8" />
    <PackageReference Include="NLog.Extensions.Logging" Version="1.6.1" />
    <PackageReference Include="NLog.WindowsIdentity" Version="4.6.8" />
  </ItemGroup>

据我所知,我好像有 nuget 包

.nuget\packages\nlog\4.6.8\lib\netstandard2.0\NLog.dll
namespace NLog.LayoutRenderers
{
    [LayoutRenderer("identity")]
    public class IdentityLayoutRenderer : LayoutRenderer

【问题讨论】:

  • 如果你使用 ${environment-user} 会发生什么?另见github.com/NLog/NLog/wiki/Environment-User-Layout-Renderer
  • 对于环境用户,我确实得到了环境变量中“USERNAME”值的内容。但是您的链接很有帮助。 “在 Windows 上,Environment.UserName 属性包含对 Windows GetUserName 函数的调用。在 Unix 平台上,UserName 属性包含对 getpwuid_r 函数的调用。”感谢您的提示!

标签: c# .net-core nlog


【解决方案1】:

来自link(感谢@granadaCoder)

NET Core 有不同的默认值。 .NET Core 中的默认主体策略是无主体。

如果您想保留 .NET Framework 的行为,请在应用的 Main 方法中调用 AppDomain.CurrentDomain.SetPrincipalPolicy(PrincipalPolicy.UnauthenticatedPrincipal)

【讨论】:

  • 我不能接受我的答案作为“答案”,直到 2 天(SOF 政策)。但我赞成这个..因为你确实在链接中找到了神奇的段落!
  • 超级加号,用于为未来的读者更新文档.....#goldStar
【解决方案2】:

所以里面的代码

https://github.com/NLog/NLog/blob/dev/src/NLog/LayoutRenderers/IdentityLayoutRenderer.cs

这是主要的代码:

    private static IIdentity GetValue()
    {
        var currentPrincipal = System.Threading.Thread.CurrentPrincipal;
        return currentPrincipal?.Identity;
    }

当我运行下面的代码时(稍微编辑一下,看看它做了什么)

        var currentPrincipal = System.Threading.Thread.CurrentPrincipal;
        var ident = currentPrincipal?.Identity;

ident 为空。

这就是为什么我在日志文件中什么也没有得到......代码解析为空。

goFigure

所以在做了一些功课之后。

Thread.CurrentPrincipal 故意为空。

在 ASP.NET CORE 中,人们会做这样的事情(我找到的典型互联网答案)

您基本上利用了完整的依赖注入大修......并使用它。

使用 DI 方法,您是否不依赖 System.Threading.Thread.CurrentPrincipal; “在身边”。 (继续阅读以解决此问题)

public void ConfigureServices(IServiceCollection services)
{
    services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();
    services.AddTransient<IPrincipal>(
        provider => provider.GetService<IHttpContextAccessor>().HttpContext.User);

    // ...
}

使用 DotNet.Core(控制台应用程序).​​..您可能必须添加一个

下面的伪代码

public void ConfigureServices(IServiceCollection services)
{
    ClaimsPrincipal myprinc = new ClaimsPrincipal(  /* you'll need a ClaimsIdentity and some claims here probably */ );

    //or
    GenericPrincipal myprinc = new GenericPrincipal ( /* you'll need GenericIdentity and some roles here probably */ );


    services.AddTransient<IPrincipal>(
        provider => myprinc);

    // ...
}

所以这不是 NLog 问题。这就是 DotNetCore 处理 System.Threading.Thread.CurrentPrincipal 的方式;不同。

这是一个很好的阅读:

https://davidpine.net/blog/principal-architecture-changes/

现在解决方法:

我已经确认如果我这样做:

AppDomain.CurrentDomain.SetPrincipalPolicy(System.Security.Principal.PrincipalPolicy.WindowsPrincipal);
    
var currentPrincipal = System.Threading.Thread.CurrentPrincipal;
var ident = currentPrincipal?.Identity;

我得到了我(过去)期望的东西!

以及日志消息。

2020/02/19 12:03:40.617|INFO|MyCompany.MyObject|***|MyDomain\MyUserName|****|HeyYouThere |

我需要在我的 linux 机器上运行,看看会发生什么(如果我有时间的话)。也许是“当前上下文中不存在”异常??

请不要盲目使用“AppDomain.CurrentDomain.SetPrincipalPolicy”。 阅读有关为什么 System.Threading.Thread.CurrentPrincipal 的 davidpine 文章;是老派。 DI 可能是未来更好的方法。

还有(如果您选择使用):

这里是枚举:

https://docs.microsoft.com/en-us/dotnet/api/system.security.principal.principalpolicy?view=netcore-3.1

字段

NoPrincipal 1 不应有任何主体或身份对象 已创建。

UnauthenticatedPrincipal 0 主体和身份对象 应该创建未经身份验证的实体。未经身份验证的实体 将 Name 设置为空字符串 ("") 并将 IsAuthenticated 设置为 假的。

WindowsPrincipal 2 反映 与当前执行线程关联的操作系统令牌 应该创建,并且相关的操作系统组应该 被映射到角色中。

您应该考虑每个值。如果需要,您应该考虑“Linux 上会发生什么”问题。

这会发生吗?

"'此平台不支持 Windows 主体功能。'"

【讨论】:

  • 这可能是问题所在:github.com/dotnet/runtime/issues/29151
  • 来自您的链接:“.NET Core 具有不同的默认值。.NET Core 中的默认主体策略是无主体。如果您想保留 .NET Framework 行为,请在 Main 中调用 AppDomain.CurrentDomain.SetPrincipalPolicy(PrincipalPolicy.UnauthenticatedPrincipal)您的应用程序的方法。”
  • 是的,这完全是学习曲线,与核心不同。我会通过 SetPrincipalPolicy .. 但会在这个答案中发布一些额外的内容。感谢您的来电。
  • 我将此作为单独的答案发布,但也许您应该更改答案,我可以删除我的答案。
猜你喜欢
  • 2019-05-26
  • 2020-06-25
  • 1970-01-01
  • 2019-12-29
  • 1970-01-01
  • 2018-04-05
  • 2016-11-02
  • 2023-04-10
  • 2018-04-11
相关资源
最近更新 更多