Данное руководство устарело. Актуальное руководство: Руководство по ASP.NET Core 7
ASP.NET Core имеет встроенную поддержку логгирования, что позволяет применять логгирование с минимальными вкраплениями кода в функционал приложения.
Для логгирования данных нам необходим объект ILogger<T>. По умолчанию среда ASP NET Core через механизм внедрения зависимостей
уже предоставляет нам такой объект. Например, возьмем стандартный проект по типу Empty и добавим механизм логгирования. Для этого перейдем к классу Startup и изменим его метод Configure()
:
using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Http; using Microsoft.Extensions.Hosting; using Microsoft.Extensions.Logging; namespace HelloApp { public class Startup { public void Configure(IApplicationBuilder app, ILogger<Startup> logger) { app.Run(async (context) => { // пишем на консоль информацию logger.LogInformation("Processing request {0}", context.Request.Path); //или так //logger.LogInformation($"Processing request {context.Request.Path}"); await context.Response.WriteAsync("Hello World!"); }); } } }
Средой выполнения в метод Configure передается объект ILogger, который представляет логгер. А метод логгера logger.LogInformation
передает на консоль некоторую информацию.
По умолчанию информация логгируется на консоль, поэтому для тестирования логгера нам надо запустить приложение как консольное:
При обращении к приложению с помощью следующего запроса http://localhost:xxxxx/index на консоль будет выведена информация, переданная логгером:
Важно, что, если мы используем класс Startup для логгирования, то получить объект логгера мы можем только в методе Configure()
,
но никак не в методе ConfigureServices()
или конструкторе класса Startup, поскольку инфраструктура логгирования зависит от конфигурации и контейнера DI, который окончательно устанавливаются
лишь после завершения работы метода ConfigureServices.
В примере выше в метод передается не просто объект ILogger, а объект ILogger<T> или точнее ILogger<Startup>. В данном случае "Startup" указывает на категорию логгера. Обычно в качестве категории логгера выступает класс (как в данном случае Startup). В чем смысл категории? Категория задает текстовую метку, с которой ассоциируется сообщение логгера, и в выводе лога мы ее можем увидеть. Где это может быть полезно? Например, у нас есть несколько классов, где ведется логгирование - к примеру, класс Startup и несколько контроллеров. Указывая в качестве категории текущий класс, впоследствии в логее мы можем увидеть, в каком классе именно было создано сообщение лога. Поэтому, как правило, в качестве категории указывается текущий класс, но в принципе это необязательно. Например, мы можем написать так:
public class Startup { public void Configure(IApplicationBuilder app, ILogger<Program> logger) { app.Run(async (context) => { logger.LogInformation("Processing request {0}", context.Request.Path); await context.Response.WriteAsync("Hello World!"); }); } }
В данном случае в качестве категории выступает класс Program, примем, обратите внимание, полное имя этого класса. Тем не менее в качестве категории, как правило, задается имя текущего класса.
При настройке логгирования мы можем установить уровень детализации информации с помощью одного из значений перечисления LogLevel. Всего мы можем использовать следующие значения:
Trace
: используется для вывода наиболее детализированных сообщений. Подобные сообщения могут нести важную информацию о
приложении и его строении, поэтому данный уровень лучше использовать при разработке, но никак не при публикации
Debug
: для вывода информации, которая может быть полезной в процессе разработки и отладки приложения
Information
: уровень сообщений, позволяющий просто отследить поток выполнения приложения
Warning
: используется для вывода сообщений о неожиданных событиях, например, ошибках, которые не влияют не останавливают выполнение приложения,
но в то же время должны быть иследованы
Error
: для вывода информации об ошибках и исключениях, которые возникли при текущей операции и которые не могут быть обработаны
Critical
: уровень критических ошибок, которые требуют немедленной реакции - ошибками операционной системы, потерей данных в бд,
переполнение памяти диска и т.д.
None
: вывод информации в лог не применяется
Для вывода соответствующего уровня информации у объекта ILogger
определены соответствующие методы расширения:
LogDebug()
LogTrace()
LogInformation()
LogWarning()
LogError()
LogCritical()
Так, в примере выше для вывода информации на консоль использовался метод LogInformation()
.
Вывод сообщений уровня Trace по умолчанию отключен.
Каждый такой метод имеет несколько перегрузок, которые могут принимать ряд различных параметров:
string data
: строковое сообщение для лога
int eventId
: числовой идентификатор, который связан с логом. Идентификатор должен быть статическим и специфическим для
определенной части логгируемых событий.
string format
: строковое сообщения для лога, которое моет содержать параметры
object[] args
: набор параметров для строкового сообщения
Exception error
: логгируемый объект исключения
Также для логгирования определен общий метод Log(), который позволяет определить уровень логгера через один из параметров:
logger.Log(LogLevel.Information, "Requested Path: {0}", context.Request.Path);
При стандартном логгировании на консоль для каждого уровня/метода определен своя метка и цветовой маркер, которые позволяют сразу выделить сообщение соответствующего уровня. Например, при запуске следующего кода:
public void Configure(IApplicationBuilder app, ILogger<Startup> logger) { app.Run(async (context) => { logger.LogCritical("LogCritical {0}", context.Request.Path); logger.LogDebug("LogDebug {0}", context.Request.Path); logger.LogError("LogError {0}", context.Request.Path); logger.LogInformation("LogInformation {0}", context.Request.Path); logger.LogWarning("LogWarning {0}", context.Request.Path); await context.Response.WriteAsync("Hello World!"); }); }
мы получим следующий лог на консоль: