You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

.NET6项目使用NLog输出TraceId至日志失败问题排查

.NET6中NLog获取OpenTelemetry TraceId为空的解决步骤
  • 检查组件版本兼容性
    当前使用的NLog.Web.AspNetCore(5.3.2)与NLog.DiagnosticSource(5.0.0)版本不匹配,NLog生态组件建议保持主版本号一致,将NLog.DiagnosticSource升级至5.3.x版本,避免版本差异导致Activity数据无法被捕获。

  • 确保OpenTelemetry正确启用Activity传播
    在Program.cs的OpenTelemetry配置中,需明确启用DiagnosticSource instrumentation,并保证Activity传播设置正确:

    builder.Logging.AddOpenTelemetry(options =>
    {
        options.IncludeScopes = true;
        options.SetResourceBuilder(ResourceBuilder.CreateDefault().AddService("YourServiceName"));
        // 其他OTel相关配置
    });
    
    builder.Services.AddOpenTelemetry().WithTracing(tracing =>
    {
        tracing.AddAspNetCoreInstrumentation();
        // 其他追踪配置
    });
    

    同时确认已安装OpenTelemetry.Instrumentation.AspNetCore包。

  • 验证NLog的Activity捕获配置
    在nlog.config的日志target中,需启用includeScopes="true",并正确配置${activity:property=TraceId}:

    <target name="loki" xsi:type="Loki" includeScopes="true">
        <layout type="JsonLayout">
            <attribute name="traceId" layout="${activity:property=TraceId}" />
            <attribute name="message" layout="${message}" />
            <!-- 其他日志属性配置 -->
        </layout>
    </target>
    

    同时确保Program.cs中已正确注册NLog中间件:

    var logger = NLog.LogManager.Setup().LoadConfigurationFromAppSettings().GetCurrentClassLogger();
    builder.Logging.ClearProviders();
    builder.Logging.AddNLogWeb();
    app.UseNLog();
    
  • 确认日志记录在活跃Activity范围内
    若日志是在应用启动阶段、无请求上下文的后台任务中记录,此时没有活跃的Activity,${activity:property=TraceId}自然为空。这类场景可手动创建并启动Activity包裹代码块:

    using (var activity = new System.Diagnostics.Activity("BackgroundTask").Start())
    {
        logger.LogInformation("后台任务日志");
    }
    
  • 备选方案:手动注入TraceId到NLog上下文
    若上述配置仍不生效,可通过中间件将OpenTelemetry的TraceId注入到NLog映射诊断上下文(MDLC):

    app.Use(async (context, next) =>
    {
        var currentActivity = System.Diagnostics.Activity.Current;
        var traceId = currentActivity?.TraceId.ToString() ?? "unknown-trace-id";
        using (NLog.MappedDiagnosticsLogicalContext.SetScoped("TraceId", traceId))
        {
            await next();
        }
    });
    

    之后在nlog.config中使用${mdlc:item=TraceId}获取TraceId。

内容的提问来源于stack exchange,提问作者Ilya Afinogentov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.17 09:02:24