Bastian Marschall
Bastian Marschall

Reputation: 21

Setting loglevel for Azure Function using Environment variable

I'm trying to control the log level for my C# Azure Function. The goal is to change the log level without having to redeploy the function. The idea is to change the Environment variables in order to achieve this.

I added an environment variable to control the log level:

Environment variable

It doesn't seem to work, as I'm still seeing Debug and Information logging:

App Insights logs

My host.json looks like this:

{
    "version": "2.0",
    "logging": {
      "applicationInsights": {
        "samplingSettings": {
          "isEnabled": true,
          "excludedTypes": "Request"
        },
        "enableLiveMetricsFilters": true
      },
      "logLevel": {
        "default": "Debug"
      }
    }
}

And Program.cs like this:

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication()
    .ConfigureLogging(builder => builder.SetMinimumLevel(LogLevel.Debug))
    .ConfigureServices(services =>
    {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
        services.Configure<LoggerFilterOptions>(options => options.Rules.Clear());      
    })
    .Build();

host.Run();

When i run my function app locally it works as intended when i change my local.settings.json:

{
  "IsEncrypted": false,
  "Values": {
    "AzureWebJobsStorage": "UseDevelopmentStorage=true",
    "FUNCTIONS_WORKER_RUNTIME": "dotnet-isolated",
    "AzureFunctionsJobHost__logging__LogLevel__default": "Warning"
  }
}

My function:

 public class Function1
 {
     private readonly ILogger<Function1> _logger;

     public Function1(ILogger<Function1> logger)
     {
         _logger = logger;
     }
     
     [Function("LogDebug")]
     public IActionResult RunDebug([HttpTrigger(AuthorizationLevel.Function, "get", "post")] HttpRequest req)
     {
         _logger.LogDebug("***********DEBUG***********");
         return new OkObjectResult("Welcome to Azure Functions!");
     }
     
     [Function("LogInformation")]
     public IActionResult RunInformation([HttpTrigger(AuthorizationLevel.Function, "get", "post")] HttpRequest req)
     {
         _logger.LogInformation("***********INFORMATION***********");
         return new OkObjectResult("Welcome to Azure Functions!");
     }

     [Function("LogWarning")]
     public IActionResult RunWarning([HttpTrigger(AuthorizationLevel.Function, "get", "post")] HttpRequest req)
     {
         _logger.LogWarning("***********WARNING***********");
         return new OkObjectResult("Welcome to Azure Functions!");
     }
 }

Can someone shed some light on what I'm missing? Thanks in advance.

Upvotes: 0

Views: 1163

Answers (2)

Bastian Marschall
Bastian Marschall

Reputation: 21

With some help from a colleague I found a way to control the log level with the environment variables.

I changed Program.cs to the following:

var host = new HostBuilder()
    .ConfigureAppConfiguration((context, config) =>
    {
        config.AddJsonFile("host.json", optional: true);
    })
    .ConfigureFunctionsWebApplication()
    .ConfigureServices((_, services) =>
    {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
        services.Configure<LoggerFilterOptions>(options => options.Rules.Clear());
    })
    .ConfigureLogging((context, logging) =>
    {
    logging.AddConfiguration(context.Configuration.GetSection("AzureFunctionsWorker:Logging"));
    })
    .Build();

host.Run();

This change allows logging to be configured by the environment variables.

My host.json looks like this:

{
  "version": "2.0",
  "logging": {
    "console": {
      "isEnabled": true
    },
    "applicationInsights": {
      "samplingSettings": {
        "isEnabled": false,
        "excludedTypes": "Request"
      },
      "enableLiveMetrics": true,
      "enableDependencyTracking": true,
      "enablePerformanceCountersCollection": true
    },
    "logLevel": {
      "default": "Error"
    }
  }
}

I can set my environment variables according to the desired log level:

Environment variables

And the result looks like this:

Azure portal logs

Upvotes: 2

Vivek Vaibhav Shandilya
Vivek Vaibhav Shandilya

Reputation: 2616

 .ConfigureLogging(builder => builder.SetMinimumLevel(LogLevel.Debug))

you have set minimum level to Debug. This code with minimum level Debug is overriding for application insights. Its working fine locally but for portal its overriding.

host.json:

 {
    "version": "2.0",
    "logging": {
      "applicationInsights": {
        "samplingSettings": {
          "isEnabled": true,
          "excludedTypes": "Request"
        },
        "enableLiveMetricsFilters": true
      },
      "logLevel": {
        "default": "Debug"
      }
    }
}

Function.cs:

using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.Logging;
using System.ComponentModel;

namespace FunctionApp5
{
    public class Function
    {
        private readonly ILogger<Function> _logger;

        public Function(ILogger<Function> logger)
        {
            _logger = logger;
        }

        [Function("Function")]
        public IActionResult Run([HttpTrigger(AuthorizationLevel.Anonymous, "get", "post")] HttpRequest req)
        {
            _logger.LogDebug("************DEBUG***********");
            _logger.LogInformation("*************INFORMATION*************");
            _logger.LogWarning("******************WARNING**************");
            _logger.LogError("************ERROR***********");
            _logger.LogCritical("************CRITICAL***********");
            _logger.LogInformation("C# HTTP trigger function processed a request.");
            return new OkObjectResult("Welcome to Azure Functions!");
        }
    }
}

I deployed code with same and I was also getting all level logs in Application insight. but in LogStream I was getting above Warning level.

Program.cs:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication()
    .ConfigureLogging(builder => builder.SetMinimumLevel(LogLevel.Debug))
    .ConfigureServices(services =>
    {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
        services.Configure<LoggerFilterOptions>(options=>options.Rules.Clear());
    })
    .Build();

host.Run();

you need to set minimum level to Warning. I am able to see in both places in application Insights and Log Stream both

Program.cs:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication()
    .ConfigureLogging(builder => builder.SetMinimumLevel(LogLevel.Warning))
    .ConfigureServices(services =>
    {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
        services.Configure<LoggerFilterOptions>(options=>options.Rules.Clear());
    })
    .Build();

host.Run();

Upvotes: 0

Related Questions