MassTransit+EF Core报错:超过20个IServiceProvider实例创建
解决方案:EF Core 多IServiceProvider创建异常(MassTransit Outbox场景)
问题根源
异常的核心原因是每次创建ApplicationDbContext时,EF Core都会生成新的IServiceProvider实例,累计超过20次后触发警告转异常。具体诱因:
- 在
AddDbContext的配置委托中,每次都会调用dataSourceBuilder.Build()生成新的NpgsqlDataSource实例 - EF Core会根据
DbContextOptions的内容哈希缓存IServiceProvider,由于每次NpgsqlDataSource都是新对象,EF Core判定为不同配置,因此不断创建新的IServiceProvider - MassTransit的Bus Outbox定期轮询数据库(你设置了5秒间隔),每次轮询都会获取
DbContext,加速了IServiceProvider的创建速度,很快达到触发阈值
修复步骤
1. 复用NpgsqlDataSource实例
修改配置代码,提前构建NpgsqlDataSource并复用,避免每次配置DbContext时生成新实例:
var connectionString = builder.Configuration.GetConnectionString("Database"); // 提前构建并复用同一个数据源实例 var dataSourceBuilder = new NpgsqlDataSourceBuilder(connectionString); var dataSource = dataSourceBuilder.Build(); services.AddDbContext<ApplicationDbContext>(options => { options.UseNpgsql(dataSource); // 使用预构建的数据源 options.UseSnakeCaseNamingConvention(); });
2. 可选:抑制警告(仅在根源问题解决后仍有警告时使用)
如果确认已经复用数据源,但仍需消除警告,可以在DbContext配置中添加警告抑制:
services.AddDbContext<ApplicationDbContext>(options => { options.UseNpgsql(dataSource); options.UseSnakeCaseNamingConvention(); options.ConfigureWarnings(warnings => warnings.Ignore(Microsoft.EntityFrameworkCore.Diagnostics.CoreEventId.ManyServiceProvidersCreatedWarning)); });
验证
将MassTransit的QueryDelay改回5秒,运行API后观察是否再出现该异常。正常情况下,复用数据源后IServiceProvider只会创建一次,不会再触发阈值警告。
内容的提问来源于stack exchange,提问作者TheDoomDestroyer
相关产品推荐
相关产品推荐

