如何单独切换EF Core的读取与写入日志?
单独控制EF Core读取/写入操作的SQL日志开关
可以单独控制EF Core读取和写入操作的日志开关,下面提供两种实用方法:
方法一:通过日志过滤器精准区分读写操作
利用EF Core数据库命令日志的固定事件ID,在日志过滤逻辑里区分读取(查询)和写入(增删改)操作:
在Program.cs中添加日志过滤规则:
builder.Logging.AddFilter("Microsoft.EntityFrameworkCore.Database.Command", (category, level, eventId) => { // 仅保留写入操作的Information级别日志,屏蔽读取操作的同类日志 if (level == LogLevel.Information) { // EF Core的命令事件ID对应:20101=查询(读取),20102=非查询(写入),20103=标量查询 return eventId.Id == 20102; } // Warning及以上级别的日志全部保留,不做过滤 return true; });
这种方式无需额外编写复杂逻辑,直接通过EF Core内置的事件ID区分操作类型,简单高效。
方法二:自定义EF Core拦截器完全掌控日志
通过实现DbCommandInterceptor,可以更灵活地控制读写操作的日志记录,还能自定义日志内容:
1. 编写自定义拦截器
public class CommandLoggingInterceptor : DbCommandInterceptor { private readonly ILogger<CommandLoggingInterceptor> _logger; public CommandLoggingInterceptor(ILogger<CommandLoggingInterceptor> logger) { _logger = logger; } // 读取操作(如查询):这里选择不记录日志,可根据需求调整 public override InterceptionResult<DbDataReader> ReaderExecuting(DbCommand command, CommandEventData eventData, InterceptionResult<DbDataReader> result) { // 若要记录读取日志,取消下面的注释 // _logger.LogInformation("读取SQL: {Sql}", command.CommandText); return result; } // 写入操作(增删改):记录日志 public override InterceptionResult<int> NonQueryExecuting(DbCommand command, CommandEventData eventData, InterceptionResult<int> result) { _logger.LogInformation("写入SQL: {Sql}", command.CommandText); return result; } }
2. 注册拦截器到DbContext
builder.Services.AddDbContext<YourDbContext>(options => { options.UseSqlServer("你的数据库连接字符串") .AddInterceptors(new CommandLoggingInterceptor(builder.Services.BuildServiceProvider().GetRequiredService<ILogger<CommandLoggingInterceptor>>())); });
注意事项
无论用哪种方法,都需要确保appsettings.json中Microsoft.EntityFrameworkCore.Database.Command的日志级别设置为Information,否则全局日志级别会优先过滤掉相关日志,导致自定义规则失效。
内容的提问来源于stack exchange,提问作者lonix
相关产品推荐
相关产品推荐

