使用W3C的应用程序洞察中的操作_ParentId的内容

问题描述 投票:0回答:1

我目前正在使用

.NET 6.0 isolated
函数和
HTTP trigger

因为活动未填充,我添加了一个中间件,该中间件基于 W3C

traceparent
标头创建活动。

我基于 MS docs 的期望是,使用 Application Insights 时,

operation_ParentId
将直接与完成日志记录的
ParentSpanId
Activity
相关。

但这不是我所看到的。我看到的是以下

  1. 应用程序 A 使用
    traceparent = 00-3abe9f15e940badc5f1521e6eb1eb411-bfd30439c918c783-00
  2. 发送请求
  3. 在应用程序 B 的中间件中,启动一个活动并记录一条消息。我还可以验证活动的
    ParentId
    等于
    00-3abe9f15e940badc5f1521e6eb1eb411-bfd30439c918c783-00
    ParentSpanId
    等于
    bfd30439c918c783
using var requestActivity = new Activity(context.FunctionDefinition.Name);

requestActivity.SetParentId(traceParent);

requestActivity.Start();

_logger.LogInformation("Invoking '{Name}'", context.FunctionDefinition.Name);
  1. 在应用程序洞察中,我看到
    OperationId
    等于 WC3 跟踪 ID
    3abe9f15e940badc5f1521e6eb1eb411
    ,正如预期的那样。然而,
    operation_ParentId
    是我以前从未见过的跨度。它既不是
    requestActivity.SpanId
    也不是
    requestActivity.ParentSpanId

发生了什么我不明白的事情? Application Insights 在记录时是否不使用活动的

Activity

我的应用程序配置

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults(worker =>
    {
        worker.UseMiddleware<TracingMiddleware>();
    })
    .ConfigureServices(collection =>
    {
    })
    .ConfigureLogging(x=>x.AddApplicationInsights())
    .Build();

host.Run();

我的中间件功能

public async Task Invoke(FunctionContext context, FunctionExecutionDelegate next)
    {
        using var requestActivity = new Activity(context.FunctionDefinition.Name);

        SetParentId(context, requestActivity);

        requestActivity.Start();

        _logger.LogInformation("Invoking '{Name}'", context.FunctionDefinition.Name);
        var t = Activity.Current;
        
        System.Console.WriteLine();
        System.Console.WriteLine($"Activity.TraceId: {t.TraceId}");
        System.Console.WriteLine($"Activity.ParentId: {t.ParentId}");
        System.Console.WriteLine($"Activity.SpanId: {t.SpanId}");

        await next(context);

        var statusCode = (context.Items != null)
            ? context.GetHttpResponseData()?.StatusCode
            : System.Net.HttpStatusCode.OK;
        _logger.LogInformation(
            "Executed '{Name}', Result {Result}, Duration = {Duration}ms",
            context.FunctionDefinition.Name,
            statusCode,
            (DateTime.UtcNow - requestActivity.StartTimeUtc).TotalMilliseconds);

        requestActivity.Stop();
    }

更新 首先,在我看来,Application Insights 对于隔离功能来说仍然没有完全正常运行。有些值可能会丢失(例如操作名称),但只需很少的工作,使用 Application Insights SDK 您仍然可以一致地添加它。

与HTTP跨度的差异相关:在进行调用(例如HTTP调用)时,库可以启动新的子活动。这就是为什么您可以获得与预期不同的父跨度。协调自动传递跟踪信息时使用的类是

DistributedContextPropagator
。我首先根据这篇文章对其进行了一些更改,以消除子活动创建的额外层。 但是,最终我们恢复了这一点,因为 Application Insights 更喜欢您保留尽可能多的默认值。获得应用程序见解(例如应用程序地图)的良好概述比使其在我查询的跟踪语句中完美对齐更重要。

azure azure-functions azure-application-insights system.diagnostics
1个回答
0
投票

根据 MS-Doc,操作 ID 等于 TraceId。而Operation_parent Id 是Trace-ID 和Parent-ID 的组合。格式有 .

operation_ParentId
字段的格式为
<trace-id>.<parent-id>
,其中
trace-id
parent-id
都是 从请求中传递的跟踪标头中获取。

我注意到它实际上并不相同。我已经厌倦了许多可能的方法。我最终得到 The operation-ID is not equal to the Trace-ID and the Operation-parent-ID is not equal to < Trace-ID>.< Parent-ID>.

在我的中间件中,我添加了当前上下文,如下所示

             ILogger logger = context.GetLogger<MyCustomMiddleware>();

                //logger.LogInformation("From function: {message}", message);
            using var requestActivity = new Activity(context.FunctionDefinition.Name);
            //t.SetParentId(context, requestActivity);

       
        requestActivity.Start();

            logger.LogInformation("Invoking '{Name}'", context.FunctionDefinition.Name);

        //requestActivity.SetParentId(Convert.ToString(requestActivity.RootId));
        requestActivity.SetParentId(requestActivity.TraceId,requestActivity.SpanId,ActivityTraceFlags.None);
        var t = Activity.Current;
        //Activity.SetParentId(context, requestActivity,);
            //t.SetParentId(context, requestActivity)
        logger.LogInformation($"Activity.TraceId: {t.TraceId}");
        logger.LogInformation($"Activity.ParentId: {t.ParentId}");
        logger.LogInformation($"Activity.SpanId: {t.SpanId}");
        logger.LogInformation($"Activity.Id: {t.Id}");
        logger.LogInformation($"Activity.ParentSpanId: {t.ParentSpanId}");
        logger.LogInformation($"Activity.RootId: {t.RootId}");
        logger.LogInformation($"Activity.Parent: {t.Parent}");

我得到的结果。 enter image description here

请参阅此处了解我的解决方法之一,其中包含更多详细信息。

© www.soinside.com 2019 - 2024. All rights reserved.