web-dev-qa-db-fra.com

Serilog dans les fonctions Azure

Chaque méthode dans Azure Functions peut avoir un Microsoft.Extensions.Logging.ILogger Injecté pour la journalisation. En utilisant WebJobsStartup avec une classe de démarrage, vous pouvez modifier la journalisation pour utiliser Serilog en utilisant la syntaxe suivante:

[Assembly: WebJobsStartup(typeof(Startup))]
namespace MyFuncApp {
    public class Startup : IWebJobsStartup
    {
        public void Configure(IWebJobsBuilder builder)
        {
            builder.Services.AddLogging(
                lb => lb.ClearProviders()
                    .AddSerilog(
                        new LoggerConfiguration()
                            .Enrich.FromLogContext()
                            .WriteTo.Console()
                            .WriteTo.File(@"C:\Temp\MyFuncApp.log")
                            .CreateLogger(),
                        true));
        }
    }
}

Je peux également ajouter d'autres objets à la DI et les injecter soit dans les méthodes, soit dans le constructeur de la classe contenant les méthodes en utilisant par exemple builder.Services.AddSingleton<IMyInterface, MyImplementation>();

Cependant, j'aimerais beaucoup pouvoir injecter le Microsoft.Extensions.Logging.ILogger De la même manière, mais si j'essaie d'utiliser le ILogger dans le constructeur, j'obtiens l'erreur suivante lors de l'invocation de la méthode (comme c'est à ce moment que la classe est créée):

Microsoft.Extensions.DependencyInjection.Abstractions: impossible de résoudre le service pour le type "Microsoft.Extensions.Logging.ILogger" lors de la tentative d'activation de "MyFuncApp.MyFunctions".

Alors, existe-t-il un moyen d'injecter le ILogger dans un constructeur de classe comme celui-ci?

public class MyFunctions
{
    private IMyInterface _myImpl;
    private ILogger _log;

    public MyFunctions(
        IMyInterface myImplememtation, // This works
        ILogger log) // This does not
    {
        _myImpl = myImplementation;
        _log = log;
        _log.LogInformation("Class constructed");
    }

    public async Task<IActionResult> Function1([HttpTrigger() ... ) {
        _log.LogInformation("Function1 invoked");
    }
}
6
GTHvidsten

Il est possible de simplifier davantage la configuration nécessaire en utilisant le package Anotar.Serilog.Fody (et tout autre Anotar package d'ailleurs)

Vous devez configurer Serilog tout de même dans la classe Startup.

Cependant, avec le package Fody, vous pouvez complètement vous débarrasser de l'enregistreur injecté

using Anotar.Serilog;

public class Functions
{
    [FunctionName("Token")]
    public async Task<IActionResult> Function1(
        [HttpTrigger()]...)
    {
        // static calls to the LogTo class
        // get translated into proper Serilog code during build
        LogTo.Information("Function1 invoked");
    }
}
1
Tomasz Pluskiewicz