Как добавить два файла логгера в ядро ​​.net с помощью LoggerFactory - PullRequest
0 голосов
/ 10 октября 2018
public class Startup
{
    public IConfiguration Configuration { get; } 

    public void ConfigureServices(IServiceCollection services)
    {   
        loggerFactory.AddFile(logFilePath1);
        services.AddSingleton<ILoggerFactory>(loggerFactory);

        loggerFactory.AddFile(logFilePath2);
        services.AddSingleton<ILoggerFactory>(loggerFactory);
    }
}

С помощью класса startup.cs я создаю два регистратора.Так как у него есть два регистратора, как я могу установить данные Ilogger в контроллере?это можно сделать, используя обычный способ?Или есть другой способ передать имя файла регистратора при входе в систему в контроллере?

1 Ответ

0 голосов
/ 10 октября 2018

ОК, так что вы хотите иметь два разных регистратора в одном контроллере, и вы хотите, чтобы эти два регистратора регистрировали разные файлы.Ведение журнала .NET Core не имеет хорошей поддержки для этого сценария, поэтому для этого требуется небольшой взлом.Всякий раз, когда я оказываюсь в ситуации, когда я получаю большое сопротивление со стороны фреймворка, который я использую, я пересматриваю, является ли то, что я пытаюсь сделать, хорошей идеей, и если это так, стоит ли мне использовать другой фреймворк, чтобы вы могли захотеть сделатьтот же самый.Имея это в виду, вот способ достичь того, что вы хотите.

Регистраторы могут быть идентифицированы по категории.В вашем случае вы хотите, чтобы на одном контроллере было два разных регистратора, поэтому вы должны использовать ILoggerFactory для создания регистраторов (вы можете использовать общий интерфейс ILogger<T>, но это становится немного странным, потому что вам нужно два разных типа для T):

public class MyController : Controller
{
    private readonly ILogger logger1;
    private readonly ILogger logger2;

    public Controller1(ILoggerFactor loggerFactory)
    {
        logger1 = loggerFactory.Create("Logger1");
        logger2 = loggerFactory.Create("Logger2");
    }
}

Категории регистраторов: Logger1 и Logger2.

Каждый регистратор по умолчанию регистрирует всех настроенных поставщиков.Вы хотите, чтобы регистратор с одной категорией входил в систему с одним провайдером, а регистратор с другой категорией - для регистрации с другим провайдером.

Хотя вы можете создавать фильтры на основе категории, поставщика и уровня журнала, проблема заключается в том, что выхочу использовать одного и того же провайдера для обеих категорий.Поставщики идентифицируются по их типу, поэтому вы не можете создать правило для конкретного экземпляра поставщика.Если вы создадите правило для провайдера файлов, это повлияет на всех сконфигурированных провайдеров файлов.

Итак, вот где начинается взлом: вы должны создать свои собственные типы провайдеров, которые связаны сфайлы для фильтрации по каждому файлу.

.NET Core не поддерживает запись в файлы, поэтому вам нужен сторонний поставщик.Вы не указали, какого провайдера вы используете, поэтому в этом примере я буду использовать приемник файлов Serilog вместе с провайдером Serilog, который позволяет подключать регистратор Serilog к каркасу ведения .NET Core.

Чтобы иметь возможностьфильтр по провайдеру вы должны создать свой провайдер.К счастью, это легко сделать, исходя из SerilogLoggerProvider:

class SerilogLoggerProvider1 : SerilogLoggerProvider
{
    public SerilogLoggerProvider1(Serilog.ILogger logger) : base(logger) { }
}

class SerilogLoggerProvider2 : SerilogLoggerProvider
{
    public SerilogLoggerProvider2(Serilog.ILogger logger) : base(logger) { }
}

Эти два провайдера не добавляют никакой функциональности, но позволяют вам создать фильтр, нацеленный на конкретного провайдера.

ДалееШаг состоит в создании двух разных регистраторов Serilog, которые регистрируют разные файлы:

var loggerConfiguration1 = new LoggerConfiguration()
    .WriteTo.File("...\1.log");
var loggerConfiguration2 = new LoggerConfiguration()
    .WriteTo.File("...\2.log");
var logger1 = loggerConfiguration1.CreateLogger();
var logger2 = loggerConfiguration2.CreateLogger();

Вы настраиваете вход в систему Main, вызывая метод расширения .ConfigureLogging:

.ConfigureLogging((hostingContext, loggingBuilder) =>
    {
        loggingBuilder
            .AddProvider(new SerilogLoggerProvider1(logger1))
            .AddFilter("Logger1", LogLevel.None)
            .AddFilter<SerilogLoggerProvider1>("Logger1", LogLevel.Information)
            .AddProvider(new SerilogLoggerProvider2(logger2))
            .AddFilter("Logger2", LogLevel.None)
            .AddFilter<SerilogLoggerProvider2>("Logger2", LogLevel.Information);
    })

Каждый провайдер(который связан с конкретным файлом), и затем для каждого поставщика настраиваются два фильтра.Я считаю, что правила оценки фильтров трудно рассуждать, но два добавленных фильтра - один с LogLevel.None, а другой с LogLevel.Information - на самом деле достигают желаемого результата, гарантируя, что сообщения журнала для двух разных категорий будут правильно перенаправляться в две разныепровайдеры.При добавлении третьего поставщика эти фильтры не будут затронуты, и сообщения из обеих категорий будут регистрироваться третьим поставщиком.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...