此示例的完整详细信息:https://download.csdn.net/download/hefeng_aspnet/89998498
Serilog 是一个日志库,它提供对文件、控制台和其他几个地方的记录。它易于配置,并且具有干净且易于使用的界面。
Serilog具有无与伦比的输出目的地选择(称为Sinks)以及丰富、路由、过滤和格式化结构化日志事件的能力,使其在任何应用程序中都不可或缺。
在本文中,我们将学习如何在 .NET 6.0 中配置和使用 Serilog,遵循保持代码整洁和高性能的最佳实践。
先决条件
Visual Studio 2022 (.NET 6.0)
Nuget包Serilog.AspNetCore,Serilog.Enrichers.CorrelationId,Serilog.Exceptions和Serilog.Sinks.Async
应用程序编程接口
在API program.cs类 中,按照以下代码进行配置:
program.cs:
using Sample.Serilog.WebApi.Core.Extensions;
using Sample.Serilog.WebApi.Core.Middlewares;
using Serilog;
try
{
var builder = WebApplication.CreateBuilder(args);
SerilogExtension.AddSerilogApi(builder.Configuration);
builder.Host.UseSerilog(Log.Logger);
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
var app = builder.Build();
app.UseMiddleware<ErrorHandlingMiddleware>();
app.UseMiddleware<RequestSerilLogMiddleware>();
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.MapControllers();
app.Run();
}
catch (Exception ex)
{
Log.Fatal(ex, "Host terminated unexpectedly");
}
finally
{
Log.Information("Server Shutting down...");
Log.CloseAndFlush();
}
最好在应用程序开始时配置Serilog并包含错误处理( try和catch)以收集和显示应用程序可能生成的任何异常。
builder.Host.UseSerilog(Log.Logger)代码负责将Serilog注册为应用程序的默认提供程序,因此也可以使用ILogger接口来注册应用程序的日志。
AddSerilogApi ()扩展包含以下代码:
SerilogExtension.cs:
namespace Sample.Serilog.WebApi.Core.Extensions;
public static class SerilogExtension
{
public static void AddSerilogApi(IConfiguration configuration)
{
Log.Logger = new LoggerConfiguration()
.MinimumLevel.Override("Microsoft.AspNetCore", LogEventLevel.Information)
.Enrich.FromLogContext()
.Enrich.WithExceptionDetails()
.Enrich.WithCorrelationId()
.Enrich.WithProperty("ApplicationName", $"API Serilog - {Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT")}")
.Filter.ByExcluding(Matching.FromSource("Microsoft.AspNetCore.StaticFiles"))
.Filter.ByExcluding(z => z.MessageTemplate.Text.Contains("Business error"))
.WriteTo.Async(wt => wt.Console(outputTemplate: "[{Timestamp:HH:mm:ss} {Level:u3}] {Message:lj} {Properties:j}{NewLine}{Exception}"))
.CreateLogger();
}
}
其中我们有以下描述:
1、MaximumLevel.Override:配置给定命名空间的最小日志记录。
2、Enrich.FromLogContext: Serilog主要工作上下文。几乎在所有情况下您都需要记录此代码片段才能获得日志记录提供程序的好处。
3、Enrich.WithExceptionDetails:发生错误时,收集并记录所有异常详细信息。
4、Enrich.WithCorrelationId:关联所有日志记录,方便追踪。
5、Enrich.WithProperty:向日志添加新的自定义属性。
6、Filter.ByExclusion:根据配置的Matching排除收集到的日志。
7、WriteTo.Async:异步执行所有操作(后台)。这是Serilog最重要的设置之一。
在app.UseMiddleware<ErrorHandlingMiddleware>()中,我们有以下代码:
提到的,该中间件用作全局错误处理。
app.UseMiddleware<RequestSerilLogMiddleware>()部分包含以下代码:
ErrorHandlingMiddleware.cs:
namespace Sample.Serilog.WebApi.Core.Middlewares;
public class ErrorHandlingMiddleware
{
private readonly RequestDelegate next;
public ErrorHandlingMiddleware(RequestDelegate next)
{
this.next = next;
}
public async Task Invoke(HttpContext context)
{
try
{
await next(context);
}
catch (Exception ex)
{
await HandleExceptionAsync(context, ex);
}
}
private static Task HandleExceptionAsync(HttpContext context, Exception exception)
{
Log.Error(exception, "Error");
var code = HttpStatusCode.InternalServerError;
var result = System.Text.Json.JsonSerializer.Serialize(new { error = exception?.Message });
context.Response.ContentType = "application/json";
context.Response.StatusCode = (int)code;
return context.Response.WriteAsync(result);
}
}
正如这篇文章中提到的,该中间件用作全局错误处理。
app.UseMiddleware<RequestSerilLogMiddleware>()部分包含以下代码:
RequestSerilLogMiddleware.cs:
namespace Sample.Serilog.WebApi.Core.Middlewares;
public class RequestSerilLogMiddleware
{
private readonly RequestDelegate _next;
public RequestSerilLogMiddleware(RequestDelegate next)
{
_next = next;
}
public Task Invoke(HttpContext context)
{
using (LogContext.PushProperty("UserName", context?.User?.Identity?.Name ?? "anônimo"))
{
return _next.Invoke(context);
}
}
}
该中间件用于收集附加信息以丰富日志,在这种情况下,我们仅收集来自认可用户的信息。
最后使用以下代码配置控制器:
ClientController.cs:
namespace Sample.Serilog.WebApi.Controllers;
[ApiController]
[Route("[controller]")]
public class ClientController : ControllerBase
{
private readonly ILogger<ClientController> _logger;
public ClientController(ILogger<ClientController> logger)
{
_logger = logger;
}
[HttpGet]
public async Task<IActionResult> Get()
{
_logger.LogInformation("Endpoint Get successful. (from ILogger)");
Log.Information("Endpoint Get successful. (from Serilog)");
return Ok();
}
}
在此示例中,我们以两种方式记录日志,一种使用ILogger ,另一种使用Serilog的名为Log的静态类。
测试
要进行测试,请 在 Swagger 中运行GET /client端点 并检查日志收集的结果,包括控制器中配置的两种形式,如下图所示:
Serilog是所有 .NET 应用程序中一个出色且不可或缺的组件,使用它您可以捕获所有应用程序日志,以便将来进行遥测分析以做出决策。使用WriteTo.Async配置,所有内容都会异步记录,这确保Serilog不会影响应用程序的性能。
此示例的完整详细信息:https://download.csdn.net/download/hefeng_aspnet/89998498
如果您喜欢此文章,请收藏、点赞、评论,谢谢,祝您快乐每一天。