CodeMonkey
CodeMonkey

Reputation: 12424

Some logs don't reach appinsights with isolated function app

I got a C# Azure function app and it uses an ILogger to log to app insight.

Until recently, the function app was implemented using .NET 6 and everything was fine. I then converted it to use .NET 8 and it's now dotnet-isolated.

Ever since the change, it seems like I'm losing log entries whenever I'm logging inside loops.. I do see all logs which are not inside loops, but it seems like after the conversion, it's like it can't handle fast logging to app insight? What can be done to solve it?

CSProj file:

<Project Sdk="Microsoft.NET.Sdk">


<PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <AzureFunctionsVersion>v4</AzureFunctionsVersion>
    <OutputType>Exe</OutputType>
    <ImplicitUsings>enabled</ImplicitUsings>
  </PropertyGroup>
  <ItemGroup>
    <Content Include="local.settings.json" />
  </ItemGroup>
  <ItemGroup>
    <PackageReference Include="IdentityModel" Version="7.0.0" />
    <PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
    <PackageReference Include="RT.Comb" Version="4.0.1" />
    <PackageReference Include="SharpZipLib" Version="1.4.2" />
    <PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.8" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="8.0.8" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="8.0.8" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.2.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.17.4" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.23.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore" Version="1.3.2" />
  </ItemGroup>
  <ItemGroup>
    <None Update="host.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
    </None>
    <None Update="local.settings.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
      <CopyToPublishDirectory>Never</CopyToPublishDirectory>
    </None>
  </ItemGroup>
  <ItemGroup>
    <Folder Include="Migrations\" />
  </ItemGroup>
  <ItemGroup>
    <Using Include="System.Threading.ExecutionContext" Alias="ExecutionContext" />
  </ItemGroup>
</Project>

This is my host.json:

{
  "version": "2.0",
  "functionTimeout": "02:00:00",
  "logging": {
    "logLevel": {
      "default": "Trace"
    },
    "applicationInsights": {
      "samplingSettings": {
        "isEnabled": false
      }
    }
  }
}

Upvotes: 0

Views: 159

Answers (2)

Rohit Sharma
Rohit Sharma

Reputation: 189

By default it just log the Error not any other log. We need to add the settings to ensure it logs everything or what we need.

Sharing my code which I added to log information logs also.

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication()
    .ConfigureServices((context, services) =>
    {
        CompositionRoot.Configure(services);
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
    }).ConfigureLogging((context, logging) =>
    {
        logging.ClearProviders();

        if (Environment.GetEnvironmentVariable("AZURE_FUNCTION_ENVIRONMENT") == "Development")
            logging.AddConsole(); //NOSONAR

        logging.AddApplicationInsights(options => { });
        logging.AddFilter<ApplicationInsightsLoggerProvider>("", LogLevel.None);
        logging.AddFilter<ApplicationInsightsLoggerProvider>("<NameSpace>", LogLevel.Information);
    })
    .Build();

host.Run();

Upvotes: 0

Sirra Sneha
Sirra Sneha

Reputation: 1085

I created a sample .NET 6 Azure Function App and then migrated it to .NET 8, can successfully see the Application Insights logs from the loop.

  • While migrating from .NET 6 to .NET 8, we may encounter issues due to NuGet packages not being installed correctly. So, ensure that the packages are upgraded accordingly.
  • I've referred this doc for migration.

I've added the below logic to print log messages from 1 to 1000 in a loop.

for (int i = 0; i < 1000; i++)
{
    _logger.LogInformation($"Logging message number {i + 1}");
    await Task.Delay(10);
}
var response = req.CreateResponse(System.Net.HttpStatusCode.OK);

Function1.cs:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Azure.Functions.Worker.Http;
using Microsoft.Extensions.Logging;
using System.Threading.Tasks;
namespace MyFunctionApp
{
    public class Function1
    {
        private readonly ILogger<Function1> _logger;
        public Function1(ILogger<Function1> logger)
        {
            _logger = logger;
        }
        [Function("Function1")]
        public async Task<HttpResponseData> Run(
            [HttpTrigger(AuthorizationLevel.Function, "get", "post")] HttpRequestData req)
        {
            _logger.LogInformation("C# HTTP trigger function processed a request.");

            for (int i = 0; i < 1000; i++)
            {
                _logger.LogInformation($"Logging message number {i + 1}");
                await Task.Delay(10);
            }
            var response = req.CreateResponse(System.Net.HttpStatusCode.OK);
            response.Headers.Add("Content-Type", "text/plain; charset=utf-8");
            response.WriteString("Welcome to Azure Functions!");
            return response;
        }
    }
}

Program.cs:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices(services =>
    {
        services.AddApplicationInsightsTelemetryWorkerService();
    })
    .Build();
await host.RunAsync();

.csproj:

<Project Sdk="Microsoft.NET.Sdk">
    <PropertyGroup>
        <TargetFramework>net8.0</TargetFramework>   <AzureFunctionsVersion>v4</AzureFunctionsVersion>
        <OutputType>Exe</OutputType>
        <ImplicitUsings>enable</ImplicitUsings>
        <Nullable>enable</Nullable>
    </PropertyGroup>
    <ItemGroup>             
        <PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.23.0" />
        <PackageReference Include="Microsoft.Azure.Functions.Worker.Extensions.Http" Version="3.2.0" />
        <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.17.4" />
        <PackageReference Include="Microsoft.ApplicationInsights.WorkerService" Version="2.22.0" />
        <PackageReference Include="Microsoft.Azure.Functions.Worker.ApplicationInsights" Version="1.2.0" />     
        <PackageReference Include="Microsoft.EntityFrameworkCore" Version="8.0.8" />
        <PackageReference Include="Microsoft.Extensions.Logging.ApplicationInsights" Version="2.22.0" />
        <PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
    </ItemGroup>
    <ItemGroup>
        <None Update="host.json">
            <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
        </None>
        <None Update="local.settings.json">
            <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
            <CopyToPublishDirectory>Never</CopyToPublishDirectory>
        </None>
    </ItemGroup>
    <ItemGroup>
        <Using Include="System.Threading.ExecutionContext" Alias="ExecutionContext" />
    </ItemGroup>
</Project>

local.settings.json:

{
  "IsEncrypted": false,
  "Values": {
    "AzureWebJobsStorage": "UseDevelopmentStorage=true",
    "FUNCTIONS_WORKER_RUNTIME": "dotnet-isolated",
    "APPLICATIONINSIGHTS_CONNECTION_STRING": "<Connection-string>"
  }
}

Output: enter image description here

Application Insights logs:

enter image description here

Upvotes: 0

Related Questions