Sledování vlastních operací pomocí sady Application Insights .NET SDK
Sady Application Insights SDK automaticky sledují příchozí požadavky HTTP a volání závislých služeb, jako jsou požadavky HTTP a dotazy SQL. Sledování a korelace požadavků a závislostí poskytuje přehled o odezvě a spolehlivosti celé aplikace napříč všemi mikroslužbami, které tuto aplikaci kombinují.
Existuje třída vzorů aplikací, které není možné obecně podporovat. Správné monitorování takových vzorů vyžaduje ruční instrumentaci kódu. Tento článek popisuje několik vzorů, které můžou vyžadovat ruční instrumentaci, jako je vlastní zpracování fronty a spouštění dlouhotrvajících úloh na pozadí.
Tento článek obsahuje pokyny ke sledování vlastních operací pomocí sady Application Insights SDK. Tato dokumentace je relevantní pro:
- Application Insights pro .NET (označované také jako Základní sada SDK) verze 2.4 nebo novější.
- Application Insights pro webové aplikace (spuštěné ASP.NET) verze 2.4 nebo novější.
- Application Insights pro ASP.NET Core verze 2.1 nebo novější.
Poznámka:
Následující dokumentace spoléhá na klasické rozhraní API Application Insights. Dlouhodobým plánem application Insights je shromažďovat data pomocí OpenTelemetry. Další informace najdete v tématu Povolení OpenTelemetry služby Azure Monitor pro aplikace .NET, Node.js, Python a Java a náš plán OpenTelemetry. Pokyny k migraci jsou k dispozici pro .NET, Node.js a Python.
Přehled
Operace je logická část práce spuštěná aplikací. Má název, počáteční čas, dobu trvání, výsledek a kontext spuštění, jako je uživatelské jméno, vlastnosti a výsledek. Pokud byla operace A inicializována operací B, operace B je nastavena jako nadřazená pro A. Operace může mít pouze jednu nadřazenou položku, ale může mít mnoho podřízených operací. Další informace o operacích a korelaci telemetrie najdete v tématu Korelace telemetrie Application Insights.
V sadě Application Insights .NET SDK je operace popsaná abstraktní třídou OperationTelemetry a jejími potomky RequestTelemetry a DependencyTelemetry.
Sledování příchozích operací
Webová sada SDK služby Application Insights automaticky shromažďuje požadavky HTTP pro ASP.NET aplikace, které běží v kanálu služby IIS, a všechny aplikace ASP.NET Core. Existují komunitní řešení pro jiné platformy a architektury. Pokud aplikace není podporována žádným ze standardních nebo komunitních řešení, můžete ji instrumentovat ručně.
Dalším příkladem, který vyžaduje vlastní sledování, je pracovní proces, který přijímá položky z fronty. U některých front se volání pro přidání zprávy do této fronty sleduje jako závislost. Operace vysoké úrovně, která popisuje zpracování zpráv, se neshromažďuje automaticky.
Pojďme se podívat, jak by mohly být tyto operace sledovány.
Na vysoké úrovni je úkolem vytvořit RequestTelemetry
a nastavit známé vlastnosti. Po dokončení operace budete sledovat telemetrii. Následující příklad ukazuje tento úkol.
Požadavek HTTP v aplikaci V místním prostředí Owinu
V tomto příkladu se kontext trasování rozšíří podle protokolu HTTP pro korelaci. Měli byste očekávat, že dostanete hlavičky, které jsou tam popsané.
public class ApplicationInsightsMiddleware : OwinMiddleware
{
// You may create a new TelemetryConfiguration instance, reuse one you already have,
// or fetch the instance created by Application Insights SDK.
private readonly TelemetryConfiguration telemetryConfiguration = TelemetryConfiguration.CreateDefault();
private readonly TelemetryClient telemetryClient = new TelemetryClient(telemetryConfiguration);
public ApplicationInsightsMiddleware(OwinMiddleware next) : base(next) {}
public override async Task Invoke(IOwinContext context)
{
// Let's create and start RequestTelemetry.
var requestTelemetry = new RequestTelemetry
{
Name = $"{context.Request.Method} {context.Request.Uri.GetLeftPart(UriPartial.Path)}"
};
// If there is a Request-Id received from the upstream service, set the telemetry context accordingly.
if (context.Request.Headers.ContainsKey("Request-Id"))
{
var requestId = context.Request.Headers.Get("Request-Id");
// Get the operation ID from the Request-Id (if you follow the HTTP Protocol for Correlation).
requestTelemetry.Context.Operation.Id = GetOperationId(requestId);
requestTelemetry.Context.Operation.ParentId = requestId;
}
// StartOperation is a helper method that allows correlation of
// current operations with nested operations/telemetry
// and initializes start time and duration on telemetry items.
var operation = telemetryClient.StartOperation(requestTelemetry);
// Process the request.
try
{
await Next.Invoke(context);
}
catch (Exception e)
{
requestTelemetry.Success = false;
requestTelemetry.ResponseCode;
telemetryClient.TrackException(e);
throw;
}
finally
{
// Update status code and success as appropriate.
if (context.Response != null)
{
requestTelemetry.ResponseCode = context.Response.StatusCode.ToString();
requestTelemetry.Success = context.Response.StatusCode >= 200 && context.Response.StatusCode <= 299;
}
else
{
requestTelemetry.Success = false;
}
// Now it's time to stop the operation (and track telemetry).
telemetryClient.StopOperation(operation);
}
}
public static string GetOperationId(string id)
{
// Returns the root ID from the '|' to the first '.' if any.
int rootEnd = id.IndexOf('.');
if (rootEnd < 0)
rootEnd = id.Length;
int rootStart = id[0] == '|' ? 1 : 0;
return id.Substring(rootStart, rootEnd - rootStart);
}
}
Protokol HTTP pro korelaci také deklaruje hlavičku Correlation-Context
. Kvůli jednoduchosti je tu vynechán.
Instrumentace front
Kontext trasování W3C a protokol HTTP pro předávání korelačních podrobností s požadavky HTTP, ale každý protokol fronty musí definovat, jak se stejné podrobnosti předávají ve zprávě fronty. Některé protokoly front, jako je AMQP, umožňují předávání dalších metadat. Jiné protokoly, jako je fronta služby Azure Storage, vyžadují, aby byl kontext zakódován do datové části zprávy.
Poznámka:
Trasování mezi komponentami se zatím pro fronty nepodporuje.
Pokud váš producent a příjemce posílají telemetrii do různých prostředků Application Insights, prostředí diagnostiky transakcí a mapa aplikací zobrazují transakce a kompletní mapování. V případě front se tato funkce zatím nepodporuje.
Fronta služby Service Bus
Informace o trasování najdete v tématu Distribuované trasování a korelace prostřednictvím zasílání zpráv služby Azure Service Bus.
Fronta služby Azure Storage
Následující příklad ukazuje, jak sledovat operace fronty Azure Storage a korelovat telemetrii mezi producentem, příjemcem a Azure Storage.
Fronta úložiště má rozhraní HTTP API. Všechna volání do fronty jsou sledována kolektorem závislostí Application Insights pro požadavky HTTP. Ve výchozím nastavení je nakonfigurovaná pro aplikace ASP.NET a ASP.NET Core. Další typy aplikací najdete v dokumentaci ke konzolovým aplikacím.
Můžete také chtít korelovat ID operace Application Insights s ID požadavku úložiště. Informace o tom, jak nastavit a získat klienta žádosti o úložiště a ID požadavku serveru, najdete v tématu Monitorování, diagnostika a řešení potíží se službou Azure Storage.
Zařadit do fronty
Protože fronty služby Storage podporují rozhraní HTTP API, všechny operace s frontou se automaticky sledují službou Application Insights. V mnoha případech by tato instrumentace měla stačit. Pokud chcete korelovat trasování na straně příjemce s trasováními producenta, musíte předat kontext korelace podobně jako v protokolu HTTP pro korelaci.
Tento příklad ukazuje, jak sledovat Enqueue
operaci. Můžete provádět následující akce:
- Korelace opakovaných pokusů (pokud existuje):Všichni mají jeden společný nadřazený objekt, který je operací
Enqueue
. Jinak se sledují jako podřízené příchozí žádosti. Pokud fronta obsahuje více logických požadavků, může být obtížné zjistit, které volání vedlo k opakovaným pokusům. - Korelace protokolů úložiště (pokud a v případě potřeby): Korelují se telemetrií Application Insights.
Operace Enqueue
je podřízenou nadřazenou operací. Příkladem je příchozí požadavek HTTP. Volání závislostí HTTP je podřízeným objektem Enqueue
operace a vnukem příchozího požadavku.
public async Task Enqueue(CloudQueue queue, string message)
{
var operation = telemetryClient.StartOperation<DependencyTelemetry>("enqueue " + queue.Name);
operation.Telemetry.Type = "Azure queue";
operation.Telemetry.Data = "Enqueue " + queue.Name;
// MessagePayload represents your custom message and also serializes correlation identifiers into payload.
// For example, if you choose to pass payload serialized to JSON, it might look like
// {'RootId' : 'some-id', 'ParentId' : '|some-id.1.2.3.', 'message' : 'your message to process'}
var jsonPayload = JsonConvert.SerializeObject(new MessagePayload
{
RootId = operation.Telemetry.Context.Operation.Id,
ParentId = operation.Telemetry.Id,
Payload = message
});
CloudQueueMessage queueMessage = new CloudQueueMessage(jsonPayload);
// Add operation.Telemetry.Id to the OperationContext to correlate Storage logs and Application Insights telemetry.
OperationContext context = new OperationContext { ClientRequestID = operation.Telemetry.Id};
try
{
await queue.AddMessageAsync(queueMessage, null, null, new QueueRequestOptions(), context);
}
catch (StorageException e)
{
operation.Telemetry.Properties.Add("AzureServiceRequestID", e.RequestInformation.ServiceRequestID);
operation.Telemetry.Success = false;
operation.Telemetry.ResultCode = e.RequestInformation.HttpStatusCode.ToString();
telemetryClient.TrackException(e);
}
finally
{
// Update status code and success as appropriate.
telemetryClient.StopOperation(operation);
}
}
Pokud chcete snížit množství telemetrických dat, které vaše aplikace hlásí, nebo pokud nechcete sledovat Enqueue
operaci z jiných důvodů, použijte Activity
rozhraní API přímo:
- Místo spuštění operace Application Insights vytvořte (a spusťte) novou
Activity
. Není nutné přiřazovat žádné vlastnosti s výjimkou názvu operace. - Serializace
yourActivity.Id
do datové části zprávy místooperation.Telemetry.Id
. Můžete také použítActivity.Current.Id
.
Odstranění z fronty
Enqueue
Podobně jako skutečný požadavek HTTP na frontu služby Storage se automaticky sleduje službou Application Insights. Operace Enqueue
se pravděpodobně provede v nadřazeného kontextu, například v kontextu příchozího požadavku. Sady Application Insights SDK automaticky korelují takovou operaci a její část HTTP s nadřazeným požadavkem a další telemetrií hlášenými ve stejném oboru.
Operace Dequeue
je složitá. Sada Application Insights SDK automaticky sleduje požadavky HTTP. Ale nezná kontext korelace, dokud se zpráva neanalyzuje. Požadavek HTTP není možné korelovat, aby se zpráva dostala se zbytkem telemetrie, zejména pokud se přijme více než jedna zpráva.
public async Task<MessagePayload> Dequeue(CloudQueue queue)
{
var operation = telemetryClient.StartOperation<DependencyTelemetry>("dequeue " + queue.Name);
operation.Telemetry.Type = "Azure queue";
operation.Telemetry.Data = "Dequeue " + queue.Name;
try
{
var message = await queue.GetMessageAsync();
}
catch (StorageException e)
{
operation.telemetry.Properties.Add("AzureServiceRequestID", e.RequestInformation.ServiceRequestID);
operation.telemetry.Success = false;
operation.telemetry.ResultCode = e.RequestInformation.HttpStatusCode.ToString();
telemetryClient.TrackException(e);
}
finally
{
// Update status code and success as appropriate.
telemetryClient.StopOperation(operation);
}
return null;
}
Zpracovat
V následujícím příkladu se příchozí zpráva sleduje podobným způsobem jako příchozí požadavek HTTP:
public async Task Process(MessagePayload message)
{
// After the message is dequeued from the queue, create RequestTelemetry to track its processing.
RequestTelemetry requestTelemetry = new RequestTelemetry { Name = "process " + queueName };
// It might also make sense to get the name from the message.
requestTelemetry.Context.Operation.Id = message.RootId;
requestTelemetry.Context.Operation.ParentId = message.ParentId;
var operation = telemetryClient.StartOperation(requestTelemetry);
try
{
await ProcessMessage();
}
catch (Exception e)
{
telemetryClient.TrackException(e);
throw;
}
finally
{
// Update status code and success as appropriate.
telemetryClient.StopOperation(operation);
}
}
Podobně lze instrumentovat i jiné operace fronty. Operace náhledu by měla být instrumentována podobným způsobem jako operace odstranění fronty. Instrumentace operací správy front není nutná. Application Insights sleduje operace, jako je HTTP, a ve většině případů stačí.
Při instrumentaci odstranění zprávy se ujistěte, že jste nastavili identifikátory operace (korelace). Alternativně můžete použít Activity
rozhraní API. Pak nemusíte nastavovat identifikátory operací u položek telemetrie, protože ji sada Application Insights SDK dělá za vás:
- Po vytvoření položky z fronty vytvořte novou
Activity
položku. - Slouží
Activity.SetParentId(message.ParentId)
ke korelaci protokolů příjemců a producentů. - Spusťte tlačítko
Activity
. - Sledujte operace vyřazení, zpracování a odstranění pomocí
Start/StopOperation
pomocných rutin. Proveďte to ze stejného asynchronního toku řízení (kontext spouštění). Tímto způsobem korelují správně. Activity
Zastavte .- Použijte
Start/StopOperation
nebo volejteTrack
telemetrii ručně.
Typy závislostí
Application Insights používá k přizpůsobení uživatelského rozhraní typ závislosti. Pro fronty rozpozná následující typy DependencyTelemetry
, které zlepšují prostředí pro diagnostiku transakcí:
Azure queue
pro fronty Azure StorageAzure Event Hubs
pro Azure Event HubsAzure Service Bus
pro Azure Service Bus
Dávkové zpracování
U některých front můžete s jedním požadavkem vyřadit z fronty více zpráv. Zpracování takových zpráv je pravděpodobně nezávislé a patří do různých logických operací. Operaci není možné korelovat Dequeue
s konkrétní zpracovávanou zprávou.
Každá zpráva by měla být zpracována ve vlastním asynchronním toku řízení. Další informace najdete v části Sledování odchozích závislostí.
Dlouhotrvající úlohy na pozadí
Některé aplikace spouštějí dlouhotrvající operace, které můžou být způsobené požadavky uživatelů. Z hlediska trasování/instrumentace se neliší od instrumentace požadavků nebo závislostí:
async Task BackgroundTask()
{
var operation = telemetryClient.StartOperation<DependencyTelemetry>(taskName);
operation.Telemetry.Type = "Background";
try
{
int progress = 0;
while (progress < 100)
{
// Process the task.
telemetryClient.TrackTrace($"done {progress++}%");
}
// Update status code and success as appropriate.
}
catch (Exception e)
{
telemetryClient.TrackException(e);
// Update status code and success as appropriate.
throw;
}
finally
{
telemetryClient.StopOperation(operation);
}
}
V tomto příkladu telemetryClient.StartOperation
vytvoří DependencyTelemetry
a vyplní kontext korelace. Řekněme, že máte nadřazenou operaci vytvořenou příchozími požadavky, které operaci naplánovaly. BackgroundTask
Pokud se spustí ve stejném asynchronním toku řízení jako příchozí požadavek, koreluje se s danou nadřazenou operací. BackgroundTask
a všechny vnořené položky telemetrie se automaticky korelují s požadavkem, který ji způsobil, a to i po skončení požadavku.
Když úloha začíná z vlákna na pozadí, které nemá přidruženou BackgroundTask
žádnou operaci (Activity
) nemá žádnou nadřazenou položku. Může však obsahovat vnořené operace. Všechny položky telemetrie hlášené z úkolu jsou korelovány s vytvořeným DependencyTelemetry
v BackgroundTask
.
Sledování odchozích závislostí
Můžete sledovat vlastní druh závislosti nebo operaci, kterou Application Insights nepodporuje.
Metoda Enqueue
ve frontě služby Service Bus nebo frontě služby Storage může sloužit jako příklady pro takové vlastní sledování.
Obecným přístupem ke sledování vlastních závislostí je:
- Zavolejte metodu
TelemetryClient.StartOperation
(extension), která vyplníDependencyTelemetry
vlastnosti potřebné pro korelaci a některé další vlastnosti, jako je začátek, časové razítko a doba trvání. - Nastavte další vlastní vlastnosti v objektu
DependencyTelemetry
, například název a jakýkoli jiný kontext, který potřebujete. - Proveďte volání závislostí a počkejte na něj.
- Po dokončení operace
StopOperation
zastavte. - Zpracování výjimek
public async Task RunMyTaskAsync()
{
using (var operation = telemetryClient.StartOperation<DependencyTelemetry>("task 1"))
{
try
{
var myTask = await StartMyTaskAsync();
// Update status code and success as appropriate.
}
catch(...)
{
// Update status code and success as appropriate.
}
}
}
Zrušení operace způsobí zastavení operace, takže ji můžete udělat místo volání StopOperation
.
Upozorňující
V některých případech může neošetřená výjimka bránit finally
v volání, takže operace nemusí být sledovány.
Paralelní zpracování a sledování operací
Volání StopOperation
zastaví pouze spuštěnou operaci. Pokud aktuální spuštěná operace neodpovídá té, kterou chcete zastavit, StopOperation
nic nedělá. K této situaci může dojít, pokud paralelně spustíte více operací ve stejném kontextu provádění.
var firstOperation = telemetryClient.StartOperation<DependencyTelemetry>("task 1");
var firstTask = RunMyTaskAsync();
var secondOperation = telemetryClient.StartOperation<DependencyTelemetry>("task 2");
var secondTask = RunMyTaskAsync();
await firstTask;
// FAILURE!!! This will do nothing and will not report telemetry for the first operation
// as currently secondOperation is active.
telemetryClient.StopOperation(firstOperation);
await secondTask;
Ujistěte se, že vždy voláte StartOperation
a zpracováváte operaci ve stejné asynchronní metodě, abyste izolovali operace spuštěné paralelně. Pokud je operace synchronní (nebo nesync), zabalte proces a sledujte pomocí Task.Run
.
public void RunMyTask(string name)
{
using (var operation = telemetryClient.StartOperation<DependencyTelemetry>(name))
{
Process();
// Update status code and success as appropriate.
}
}
public async Task RunAllTasks()
{
var task1 = Task.Run(() => RunMyTask("task 1"));
var task2 = Task.Run(() => RunMyTask("task 2"));
await Task.WhenAll(task1, task2);
}
Operace ApplicationInsights vs. System.Diagnostics.Activity
System.Diagnostics.Activity
představuje distribuovaný kontext trasování a je používán architekturami a knihovnami k vytvoření a šíření kontextu uvnitř procesu a mimo proces a korelaci položek telemetrie. Activity
spolupracuje s mechanismem System.Diagnostics.DiagnosticSource
oznámení mezi architekturou nebo knihovnou, aby upozorňovat na zajímavé události, jako jsou příchozí nebo odchozí požadavky a výjimky.
Aktivity jsou prvotřídními občany ve službě Application Insights. Automatické závislosti a shromažďování požadavků se na ně spoléhají společně s událostmi DiagnosticSource
. Pokud jste vytvořili Activity
ve své aplikaci, nemělo by to za následek vytvoření telemetrie Application Insights. Application Insights potřebuje přijímat DiagnosticSource
události a znát názvy událostí a datové části, které se mají překládat Activity
na telemetrii.
Každá operace Application Insights (požadavek nebo závislost) zahrnuje Activity
. Když StartOperation
je volána, vytvoří Activity
se pod ní. StartOperation
je doporučený způsob ručního sledování telemetrie požadavků nebo závislostí a zajištění korelace všeho.
Další kroky
- Seznamte se se základy korelace telemetrie v Application Insights.
- Podívejte se, jak korelovaná data řídí prostředí pro diagnostiku transakcí a mapu aplikací.
- Podívejte se na datový model pro typy Application Insights a datový model.
- Nahlašujte vlastní události a metriky do Application Insights.
- Podívejte se na standardní konfiguraci kolekce kontextových vlastností.
- Projděte si uživatelskou příručku system.Diagnostics.Activity a zjistěte, jak korelujeme telemetrii.