c# - API Application Insights 良好使用实践

标签 c# azure asp.net-mvc-5 azure-application-insights telemetry

我阅读了此文档:https://learn.microsoft.com/en-us/azure/application-insights/app-insights-api-custom-events-metrics

有许多不同的 API 方法来跟踪异常、跟踪跟踪等。

我有一个 ASP.NET MVC 5 应用程序。 例如,我有以下 Controller 方法(由ajax调用):

    [AjaxErrorHandling]
    [HttpPost]
    public async Task SyncDriverToVistracks(int DriverID)
    {
            if ([condition])
            {
                // some actions here

                try
                {
                    driver.VistrackId = await _vistracksService.AddNewDriverToVistrackAsync(domain);
                    await db.SaveChangesAsync();
                }
                catch (VistracksApiException api_ex)
                {
                    // external service throws exception type VistracksApiException 
                    throw new AjaxException("vistracksApiClient", api_ex.Response.Message);
                }
                catch (VistracksApiCommonException common_ex)
                {
                    // external service throws exception type VistracksApiCommonException 
                    throw new AjaxException("vistracksApiServer", "3MD HOS server is not available");
                }
                catch (Exception ex)
                {
                    // something wrong at all
                    throw new AjaxException("General", ex.Message);
                }
            }
            else
            {
                // condition is not valid
                throw new AjaxException("General", "AccountId is not found");
            }
    }

如果出现错误,此方法会抛出 AjaxException(由 AjaxErrorHandling 捕获,然后向客户端返回一些 json 响应)。

现在我想添加遥测技术来记录、分析异常并观察客户端事件。

因此,我添加了以下内容:

    [AjaxErrorHandling]
    [HttpPost]
    public async Task SyncDriverToVistracks(int DriverID)
    {
            telemetryClient.TrackEvent("Sync driver", new Dictionary<string, string> { { "ChangedBy", User.Identity.Name }, { "DriverID", DriverID.ToString() } }, null);
            if ([condition])
            {
                // some actions here

                try
                {
                    driver.VistrackId = await _vistracksService.AddNewDriverToVistrackAsync(domain);
                    await db.SaveChangesAsync();
                }
                catch (VistracksApiException api_ex)
                {
                    // external service throws exception type VistracksApiException 
                    telemetryClient.TrackTrace("VistracksApiException", new Dictionary<string, string> {
                        { "ChangedBy", User.Identity.Name },
                        { "DriverID", DriverID.ToString() },
                        { "ResponseCode", api_ex.Response.Code.ToString() },
                        { "ResponseMessage", api_ex.Response.Message },
                        { "ResponseDescription", api_ex.Response.Description }
                    });
                    telemetryClient.TrackException(api_ex);

                    throw new AjaxException("vistracksApiClient", api_ex.Response.Message);
                }
                catch (VistracksApiCommonException common_ex)
                {
                    // external service throws exception type VistracksApiCommonException 
                    telemetryClient.TrackTrace("VistracksApiCommonException", new Dictionary<string, string> {
                        { "ChangedBy", User.Identity.Name },
                        { "DriverID", DriverID.ToString() },
                        { "Message", common_ex.Message },
                    });
                    telemetryClient.TrackException(common_ex);
                    throw new AjaxException("vistracksApiServer", "3MD HOS server is not available");
                }
                catch (Exception ex)
                {
                    // something wrong at all
                    telemetryClient.TrackTrace("Exception", new Dictionary<string, string> {
                        { "ChangedBy", User.Identity.Name },
                        { "DriverID", DriverID.ToString() },
                        { "Message", ex.Message },
                    });
                    telemetryClient.TrackException(ex);
                    throw new AjaxException("General", ex.Message);
                }
            }
            else
            {
                telemetryClient.TrackTrace("ConditionWrong", new Dictionary<string, string> {
                    { "ChangedBy", User.Identity.Name },
                    { "DriverID", DriverID.ToString() },
                    { "Message", "AccountId is not found" },
                });
                // condition is not valid
                throw new AjaxException("General", "AccountId is not found");
            }
    }

通过以下行:

        telemetryClient.TrackEvent("Sync driver", new Dictionary<string, string> { { "ChangedBy", User.Identity.Name }, { "DriverID", DriverID.ToString() } }, null);

我只是“记录”调用该方法的客户端事件。仅供统计。

在每个“catch” block 中,我尝试使用不同的参数编写跟踪并编写异常:

                    telemetryClient.TrackTrace("trace name", new Dictionary<string, string> {
                        { "ChangedBy", User.Identity.Name },
                        ....
                    });
                    telemetryClient.TrackException(ex);

有必要吗?或者只需要跟踪异常?然后我会丢失不同的信息,例如谁尝试添加这些更改等...何时应该使用这些方法?

最佳答案

这是2.5.1 AI SDK的最佳实践。将突出显示即将发布的 AI SDK 版本中可能不需要的部分。

进行端到端跟踪的正确方法是依赖.NET框架中新的Activity类。在 AI 支持 Activity.Tags ( https://github.com/Microsoft/ApplicationInsights-dotnet/issues/562 ) 之前,您需要使用 TelemetryInitializer 手动传播它们:

public class ActvityTagsTelemetryInitializer : ITelemetryInitializer
{
    public void Initialize(ITelemetry telemetry)
    {
        Activity current = Activity.Current;

        if (current == null)
        {
            current = (Activity)HttpContext.Current?.Items["__AspnetActivity__"];
        }

        while (current != null)
        {
            foreach (var tag in current.Tags)
            {
                if (!telemetry.Context.Properties.ContainsKey(tag.Key))
                {
                    telemetry.Context.Properties.Add(tag.Key, tag.Value);
                }
            }

            current = current.Parent;
        }
    }
}

然后在ApplicationInsights.config中注册它:

  <TelemetryInitializers>
    ...
    <Add Type="<namespace>.ActvityTagsTelemetryInitializer, <assemblyname>"/>
  </TelemetryInitializers>

然后您可以填充适当的标签:

[AjaxErrorHandling]
[HttpPost]
public async Task SyncDriverToVistracks(int DriverID)
{
    Activity.Current.AddTag("DriverID", DriverID.ToString());
    Activity.Current.AddTag("UserID", User.Identity.Name);

    try
    {
        if ([condition])
        {
            // some actions here

            try
            {
                // If below call is HTTP then no need to use StartOperation
                using (telemetryClient.StartOperation<DependencyTelemetry>("AddNewDriverToVistrackAsync"))
                {
                    driver.VistrackId = await _vistracksService.AddNewDriverToVistrackAsync(domain);
                }

                // If below call is HTTP then no need to use StartOperation
                using (telemetryClient.StartOperation<DependencyTelemetry>("SaveChanges"))
                {
                    await db.SaveChangesAsync();
                }
            }
            catch (VistracksApiException api_ex)
            {
                // external service throws exception type VistracksApiException 
                throw new AjaxException("vistracksApiClient", api_ex.Response.Message);
            }
            catch (VistracksApiCommonException common_ex)
            {
                // external service throws exception type VistracksApiCommonException 
                throw new AjaxException("vistracksApiServer", "3MD HOS server is not available");
            }
            catch (Exception ex)
            {
                // something wrong at all
                throw new AjaxException("General", ex.Message);
            }
        }
        else
        {
            // condition is not valid
            throw new AjaxException("General", "AccountId is not found");
        }
    }
    catch (Exception ex)
    {
        // Upcoming 2.6 AI SDK will track exceptions for MVC apps automatically.
        telemetryClient.TrackException(ex);
        throw;
    }
}

您应该拥有以下遥测数据:

  1. 传入请求
  2. 传出请求(依赖项)
  3. 失败请求的异常(exception)情况

所有遥测数据都将带有 ChangedBy 和 DriverID 标记

关于c# - API Application Insights 良好使用实践,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49353691/

相关文章:

azure - 如何查看Azure系统默认路由

azure - 如何获取有关 azure 静态网站上的用户访问统计信息?

c# - 为什么我无法将具体泛型转换为带有接口(interface)的参数?

c# - 错误找不到类型或命名空间名称 'AxWMPLib'(是否缺少 using 指令或程序集引用?)

C# 合并 2 个字典并在它们之间添加值

javascript - addTelemetryInitializer 可以调用多少次?

c# - 在 MVC 中绑定(bind)对象数组

asp.net-mvc - ASP.NET Core 将路由映射到静态文件处理程序

c# - 在 Windows Phone 中根据颜色裁剪图像的边框

c# - 为什么 powershell 无法识别 Windows 服务调用的脚本中的 cmdlet?