如何在 .NET 8 中跨边界启动/继续活动

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

我有一些微服务运行着一堆工作负载,并且我正在尝试跟踪给定工作负载的“路线”。我正在使用 .NET Aspire,并添加了 3 个后台工作项目和一个 Web API 项目。

第一个后台工作人员在工作负载到达时启动活动。完成后,它将其推送到 RabbitMQ 队列中。我获取当前活动的 ID 并将其推送到消息的标头中。 Worker 2 在向 Worker 3 推送消息时使用相同的方法。

basicProperties.Headers = new Dictionary<String, Object>();

if (Activity.Current?.Id !=  null) 
{
    basicProperties.Headers.Add(DiagnosticsHandlerLoggingStrings.TraceParentHeaderName, Activity.Current?.Id);
}

在工作人员 2 和 3 中,我以这种方式开始一项活动:

if (basicProperties.Headers?.TryGetValue(DiagnosticsHandlerLoggingStrings.TraceParentHeaderName, out var parentActivityIdRaw) == true &&
    parentActivityIdRaw is Byte[] traceParentBytes) {
    parentActivityId = Encoding.UTF8.GetString(traceParentBytes);
}

return activitySource.StartActivity("Incoming message from queue", kind: ActivityKind.Consumer, parentId: parentActivityId);

使用

HttpClient
,第三个也是最后一个工作线程调用 Web API。

Aspire 中的跟踪页面显示了工作程序 1、工作程序 3 和 Web API。不是工作人员 2。此外,我在工作人员 3 中添加的任何事件都不会显示在详细信息视图中,只有来自

HttpClient
的事件。

enter image description here

跨界继续活动的正确方法是什么?看起来

HttpClient
IHttpActivityFeature
也可以处理它,并且实际上正在继续该活动,但是当我在自己的代码中使用
Activity.Current
时,没有任何内容放入活动的事件中,至少它没有显示在跟踪详细信息。

查看跟踪,似乎我正确设置了活动,但不知何故,我无法自己向其中添加事件,尽管

HttpClient
可以。

c# .net-8.0 otel
1个回答
0
投票

查看 @martindotnet 提供的链接并进行一些修改后,我终于让它工作了。 这是 RabbitMQ(v7 之前)的解决方案,因此跨边界推送和弹出跟踪是为此完成的,但是!

重要的是您需要在接收端启动活动。

首先是消费者/接收者:

var context = Propagators.DefaultTextMapPropagator.Extract(new PropagationContext(
        new ActivityContext(),
         Baggage.Current),
     ea.BasicProperties,
     (properties, key) => {
        if (properties.Headers?.TryGetValue(key, out var propertyValue) == true && propertyValue is Byte[] propertyValueBytes) {
            return new List<String> { Encoding.UTF8.GetString(propertyValueBytes) };
        }
        return new List<String> { };
});

using var activity = this.transparencyObservability.ActivitySource.StartActivity(
    "Consume Message",
    ActivityKind.Consumer,
    context.ActivityContext);
Activity.Current?.AddEvent(new ActivityEvent(
    "Got message from queue, unpacked, ready to handle"));

出版商:

var basicProperties = channel.CreateBasicProperties();

Propagators.DefaultTextMapPropagator.Inject(
    new PropagationContext(Activity.Current?.Context ?? default, Baggage.Current),
    basicProperties, (msg, key, value) => {
        msg.Headers.TryAdd(key, value);
});

就是这样。传播器是 OpenTelemetry 的一部分,所以没什么魔法!

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