Delen via


Een Azure Batch .NET-toepassing bewaken en fouten opsporen met Application Insights

Application Insights biedt een elegante en krachtige manier voor ontwikkelaars om toepassingen te bewaken en fouten op te sporen die zijn geïmplementeerd in Azure-services. Gebruik Application Insights om prestatiemeteritems en uitzonderingen te bewaken en uw code te instrumenteren met aangepaste metrische gegevens en tracering. Door Application Insights te integreren met uw Azure Batch-toepassing, krijgt u meer inzicht in gedrag en kunt u problemen in bijna realtime onderzoeken.

In dit artikel wordt beschreven hoe u de Application Insights-bibliotheek toevoegt en configureert in uw Azure Batch .NET-oplossing en hoe u de toepassingscode instrumenteren. U ziet ook manieren om uw toepassing te bewaken via Azure Portal en aangepaste dashboards te bouwen. Raadpleeg de documentatie over talen, platforms en integraties voor Application Insights in andere talen.

Een C#-voorbeeldoplossing met code die bij dit artikel hoort, is beschikbaar op GitHub. In dit voorbeeld wordt application Insights-instrumentatiecode toegevoegd aan het TopNWords-voorbeeld . Als u niet bekend bent met dat voorbeeld, kunt u eerst TopNWords bouwen en uitvoeren. Dit helpt u inzicht te krijgen in een eenvoudige Batch-werkstroom voor het verwerken van een set invoer-blobs parallel op meerdere rekenknooppunten.

Tip

Als alternatief configureert u uw Batch-oplossing om Application Insights-gegevens weer te geven, zoals VM-prestatiemeteritems in Batch Explorer. Batch Explorer is een gratis, uitgebreid, zelfstandig clienthulpprogramma voor het maken, opsporen en bewaken van Azure Batch-toepassingen. Download een installatiepakket voor Mac, Linux of Windows. Zie de opslagplaats batch-insights voor snelle stappen voor het inschakelen van Application Insights-gegevens in Batch Explorer.

Vereisten

Application Insights toevoegen aan uw project

Het NuGet-pakket Microsoft.ApplicationInsights.WindowsServer en de bijbehorende afhankelijkheden zijn vereist voor uw project. Voeg ze toe aan of herstel deze aan het project van uw toepassing. Gebruik de Install-Package opdracht of NuGet Pakketbeheer om het pakket te installeren.

Install-Package Microsoft.ApplicationInsights.WindowsServer

Verwijs naar Application Insights vanuit uw .NET-toepassing met behulp van de Microsoft.ApplicationInsights-naamruimte .

Instrumenteer uw code

Om uw code te instrumenteren, moet uw oplossing een Application Insights TelemetryClient maken. In het voorbeeld laadt TelemetryClient de configuratie van het ApplicationInsights.config-bestand . Zorg ervoor dat u ApplicationInsights.config bijwerkt in de volgende projecten met uw Application Insights-instrumentatiesleutel: Microsoft.Azure.Batch.Samples.TelemetryStartTask en TopNWordsSample.

<InstrumentationKey>YOUR-IKEY-GOES-HERE</InstrumentationKey>

Voeg ook de instrumentatiesleutel toe aan het bestand TopNWords.cs.

In het voorbeeld in TopNWords.cs worden de volgende instrumentatie-aanroepen van de Application Insights-API gebruikt:

  • TrackMetric() - Houdt bij hoe lang het gemiddeld duurt voordat een rekenknooppunt het vereiste tekstbestand downloadt.
  • TrackTrace() - Voegt foutopsporingsaanroepen toe aan uw code.
  • TrackEvent() - Houdt interessante gebeurtenissen bij die moeten worden vastgelegd.

In dit voorbeeld wordt de afhandeling van uitzonderingen opzettelijk weggelaten. In plaats daarvan rapporteert Application Insights automatisch niet-verwerkte uitzonderingen, waardoor de foutopsporingservaring aanzienlijk wordt verbeterd.

In het volgende codefragment ziet u hoe u deze methoden gebruikt.

public void CountWords(string blobName, int numTopN, string storageAccountName, string storageAccountKey)
{
    // simulate exception for some set of tasks
    Random rand = new Random();
    if (rand.Next(0, 10) % 10 == 0)
    {
        blobName += ".badUrl";
    }

    // log the url we are downloading the file from
    insightsClient.TrackTrace(new TraceTelemetry(string.Format("Task {0}: Download file from: {1}", this.taskId, blobName), SeverityLevel.Verbose));

    // open the cloud blob that contains the book
    var storageCred = new StorageCredentials(storageAccountName, storageAccountKey);
    CloudBlockBlob blob = new CloudBlockBlob(new Uri(blobName), storageCred);
    using (Stream memoryStream = new MemoryStream())
    {
        // calculate blob download time
        DateTime start = DateTime.Now;
        blob.DownloadToStream(memoryStream);
        TimeSpan downloadTime = DateTime.Now.Subtract(start);

        // track how long the blob takes to download on this node
        // this will help debug timing issues or identify poorly performing nodes
        insightsClient.TrackMetric("Blob download in seconds", downloadTime.TotalSeconds, this.CommonProperties);

        memoryStream.Position = 0; //Reset the stream
        var sr = new StreamReader(memoryStream);
        var myStr = sr.ReadToEnd();
        string[] words = myStr.Split(' ');

        // log how many words were found in the text file
        insightsClient.TrackTrace(new TraceTelemetry(string.Format("Task {0}: Found {1} words", this.taskId, words.Length), SeverityLevel.Verbose));
        var topNWords =
            words.
                Where(word => word.Length > 0).
                GroupBy(word => word, (key, group) => new KeyValuePair<String, long>(key, group.LongCount())).
                OrderByDescending(x => x.Value).
                Take(numTopN).
                ToList();
        foreach (var pair in topNWords)
        {
            Console.WriteLine("{0} {1}", pair.Key, pair.Value);
        }

        // emit an event to track the completion of the task
        insightsClient.TrackEvent("Done counting words");
    }
}

Helper voor initialisatie van Azure Batch-telemetrie

Bij het rapporteren van telemetrie voor een bepaalde server en instantie gebruikt Application Insights de azure-VM-rol en vm-naam voor de standaardwaarden. In de context van Azure Batch ziet u in het voorbeeld hoe u in plaats daarvan de naam van de pool en de naam van het rekenknooppunt gebruikt. Gebruik een initialisatiefunctie voor telemetrie om de standaardwaarden te overschrijven.

using Microsoft.ApplicationInsights.Channel;
using Microsoft.ApplicationInsights.Extensibility;
using System;
using System.Threading;

namespace Microsoft.Azure.Batch.Samples.TelemetryInitializer
{
    public class AzureBatchNodeTelemetryInitializer : ITelemetryInitializer
    {
        // Azure Batch environment variables
        private const string PoolIdEnvironmentVariable = "AZ_BATCH_POOL_ID";
        private const string NodeIdEnvironmentVariable = "AZ_BATCH_NODE_ID";

        private string roleInstanceName;
        private string roleName;

        public void Initialize(ITelemetry telemetry)
        {
            if (string.IsNullOrEmpty(telemetry.Context.Cloud.RoleName))
            {
                // override the role name with the Azure Batch Pool name
                string name = LazyInitializer.EnsureInitialized(ref this.roleName, this.GetPoolName);
                telemetry.Context.Cloud.RoleName = name;
            }

            if (string.IsNullOrEmpty(telemetry.Context.Cloud.RoleInstance))
            {
                // override the role instance with the Azure Batch Compute Node name
                string name = LazyInitializer.EnsureInitialized(ref this.roleInstanceName, this.GetNodeName);
                telemetry.Context.Cloud.RoleInstance = name;
            }
        }

        private string GetPoolName()
        {
            return Environment.GetEnvironmentVariable(PoolIdEnvironmentVariable) ?? string.Empty;
        }

        private string GetNodeName()
        {
            return Environment.GetEnvironmentVariable(NodeIdEnvironmentVariable) ?? string.Empty;
        }
    }
}

Als u de initialisatiefunctie voor telemetrie wilt inschakelen, bevat het bestand ApplicationInsights.config in het Project TopNWordsSample het volgende:

<TelemetryInitializers>
    <Add Type="Microsoft.Azure.Batch.Samples.TelemetryInitializer.AzureBatchNodeTelemetryInitializer, Microsoft.Azure.Batch.Samples.TelemetryInitializer"/>
</TelemetryInitializers>

De taak en taken bijwerken om binaire Application Insights-bestanden op te nemen

Zorg ervoor dat de binaire bestanden correct worden geplaatst om Application Insights correct uit te voeren op uw rekenknooppunten. Voeg de vereiste binaire bestanden toe aan de verzameling resourcebestanden van uw taak, zodat deze worden gedownload op het moment dat uw taak wordt uitgevoerd. De volgende codefragmenten zijn vergelijkbaar met code in Job.cs.

Maak eerst een statische lijst met Application Insights-bestanden die u wilt uploaden.

private static readonly List<string> AIFilesToUpload = new List<string>()
{
    // Application Insights config and assemblies
    "ApplicationInsights.config",
    "Microsoft.ApplicationInsights.dll",
    "Microsoft.AI.Agent.Intercept.dll",
    "Microsoft.AI.DependencyCollector.dll",
    "Microsoft.AI.PerfCounterCollector.dll",
    "Microsoft.AI.ServerTelemetryChannel.dll",
    "Microsoft.AI.WindowsServer.dll",
    
    // custom telemetry initializer assemblies
    "Microsoft.Azure.Batch.Samples.TelemetryInitializer.dll",
 };
...

Maak vervolgens de faseringsbestanden die door de taak worden gebruikt.

...
// create file staging objects that represent the executable and its dependent assembly to run as the task.
// These files are copied to every node before the corresponding task is scheduled to run on that node.
FileToStage topNWordExe = new FileToStage(TopNWordsExeName, stagingStorageAccount);
FileToStage storageDll = new FileToStage(StorageClientDllName, stagingStorageAccount);

// Upload Application Insights assemblies
List<FileToStage> aiStagedFiles = new List<FileToStage>();
foreach (string aiFile in AIFilesToUpload)
{
    aiStagedFiles.Add(new FileToStage(aiFile, stagingStorageAccount));
}
...

De FileToStage methode is een helperfunctie in het codevoorbeeld waarmee u eenvoudig een bestand kunt uploaden van een lokale schijf naar een Azure Storage-blob. Elk bestand wordt later gedownload naar een rekenknooppunt en waarnaar wordt verwezen door een taak.

Voeg tot slot de taken toe aan de taak en voeg de benodigde binaire Application Insights-bestanden toe.

...
// initialize a collection to hold the tasks that will be submitted in their entirety
List<CloudTask> tasksToRun = new List<CloudTask>(topNWordsConfiguration.NumberOfTasks);
for (int i = 1; i <= topNWordsConfiguration.NumberOfTasks; i++)
{
    CloudTask task = new CloudTask("task_no_" + i, String.Format("{0} --Task {1} {2} {3} {4}",
        TopNWordsExeName,
        string.Format("https://{0}.blob.core.windows.net/{1}",
            accountSettings.StorageAccountName,
            documents[i]),
        topNWordsConfiguration.TopWordCount,
        accountSettings.StorageAccountName,
        accountSettings.StorageAccountKey));

    //This is the list of files to stage to a container -- for each job, one container is created and 
    //files all resolve to Azure Blobs by their name (so two tasks with the same named file will create just 1 blob in
    //the container).
    task.FilesToStage = new List<IFileStagingProvider>
                        {
                            // required application binaries
                            topNWordExe,
                            storageDll,
                        };
    foreach (FileToStage stagedFile in aiStagedFiles)
   {
        task.FilesToStage.Add(stagedFile);
   }    
    task.RunElevated = false;
    tasksToRun.Add(task);
}

Gegevens weergeven in de Azure-portal

Nu u de taak en taken hebt geconfigureerd voor het gebruik van Application Insights, voert u de voorbeeldtaak uit in uw pool. Navigeer naar Azure Portal en open de Application Insights-resource die u hebt ingericht. Nadat de pool is ingericht, moet u beginnen met het weergeven van gegevensstromen en het vastleggen van logboeken. De rest van dit artikel heeft betrekking op slechts enkele Application Insights-functies, maar u kunt de volledige functieset verkennen.

Livestreamgegevens weergeven

Als u traceringslogboeken in uw Applications Insights-resource wilt weergeven, klikt u op Live Stream. In de volgende schermopname ziet u hoe u livegegevens weergeeft die afkomstig zijn van de rekenknooppunten in de pool, bijvoorbeeld het CPU-gebruik per rekenknooppunt.

Schermopname van de gegevens van het rekenknooppunt van de livestream.

Traceringslogboeken weergeven

Als u traceringslogboeken in uw Applications Insights-resource wilt weergeven, klikt u op Zoeken. In deze weergave ziet u een lijst met diagnostische gegevens die zijn vastgelegd door Application Insights, waaronder traceringen, gebeurtenissen en uitzonderingen.

In de volgende schermopname ziet u hoe één tracering voor een taak wordt geregistreerd en later wordt opgevraagd voor foutopsporingsdoeleinden.

Schermopname van logboeken voor één tracering.

Niet-verwerkte uitzonderingen weergeven

Application Insights registreert uitzonderingen die zijn gegenereerd vanuit uw toepassing. In dit geval kunt u binnen enkele seconden na het genereren van de uitzondering inzoomen op een specifieke uitzondering en het probleem vaststellen.

Schermopname van niet-verwerkte uitzonderingen.

Downloadtijd voor blob meten

Aangepaste metrische gegevens zijn ook een waardevol hulpmiddel in de portal. U kunt bijvoorbeeld de gemiddelde tijd weergeven die nodig was voor elk rekenknooppunt om het vereiste tekstbestand te downloaden dat het verwerken was.

Een voorbeeldgrafiek maken:

  1. Klik in uw Application Insights-resource op Metrics Explorer>- grafiek toevoegen.
  2. Klik op Bewerken in de grafiek die is toegevoegd.
  3. Werk de grafiekdetails als volgt bij:
    • Stel het grafiektype in op Raster.
    • Stel Aggregatie in op Gemiddelde.
    • Stel Groeperen op in NodeId.
    • Selecteer in Metrische gegevens de optie Aangepaste>blobdownload in seconden.
    • Pas het kleurenpalet van de weergave aan uw keuze aan.

Schermopname van een grafiek met de downloadtijd van de blob per knooppunt.

Rekenknooppunten continu bewaken

Mogelijk hebt u gemerkt dat alle metrische gegevens, inclusief prestatiemeteritems, alleen worden geregistreerd wanneer de taken worden uitgevoerd. Dit gedrag is handig omdat hiermee de hoeveelheid gegevens wordt beperkt die Application Insights registreert. Er zijn echter gevallen waarin u altijd de rekenknooppunten wilt bewaken. Ze kunnen bijvoorbeeld achtergrondwerk uitvoeren dat niet is gepland via de Batch-service. In dit geval stelt u een bewakingsproces in dat moet worden uitgevoerd voor de levensduur van het rekenknooppunt.

Een manier om dit gedrag te bereiken, is door een proces te maken dat de Application Insights-bibliotheek laadt en op de achtergrond wordt uitgevoerd. In het voorbeeld worden met de begintaak de binaire bestanden op de computer geladen en wordt een proces voor onbepaalde tijd uitgevoerd. Configureer het Application Insights-configuratiebestand voor dit proces om extra gegevens te verzenden waarin u geïnteresseerd bent, zoals prestatiemeteritems.

...
 // Batch start task telemetry runner
private const string BatchStartTaskFolderName = "StartTask";
private const string BatchStartTaskTelemetryRunnerName = "Microsoft.Azure.Batch.Samples.TelemetryStartTask.exe";
private const string BatchStartTaskTelemetryRunnerAIConfig = "ApplicationInsights.config";
...
CloudPool pool = client.PoolOperations.CreatePool(
    topNWordsConfiguration.PoolId,
    targetDedicated: topNWordsConfiguration.PoolNodeCount,
    virtualMachineSize: "standard_d1_v2",
    VirtualMachineConfiguration: new VirtualMachineConfiguration(
    imageReference: new ImageReference(
                        publisher: "MicrosoftWindowsServer",
                        offer: "WindowsServer",
                        sku: "2019-datacenter-core",
                        version: "latest"),
    nodeAgentSkuId: "batch.node.windows amd64");
...

// Create a start task which will run a dummy exe in background that simply emits performance
// counter data as defined in the relevant ApplicationInsights.config.
// Note that the waitForSuccess on the start task was not set so the Compute Node will be
// available immediately after this command is run.
pool.StartTask = new StartTask()
{
    CommandLine = string.Format("cmd /c {0}", BatchStartTaskTelemetryRunnerName),
    ResourceFiles = resourceFiles
};
...

Tip

Als u de beheerbaarheid van uw oplossing wilt vergroten, kunt u de assembly bundelen in een toepassingspakket. Als u vervolgens het toepassingspakket automatisch wilt implementeren in uw pools, voegt u een verwijzing naar het toepassingspakket toe aan de poolconfiguratie.

Beperking en voorbeeldgegevens

Vanwege de grootschalige aard van Azure Batch-toepassingen die in productie worden uitgevoerd, wilt u mogelijk de hoeveelheid gegevens beperken die door Application Insights worden verzameld om de kosten te beheren. Zie Sampling in Application Insights voor enkele mechanismen om dit te bereiken.

Volgende stappen