.Net 4.8 MVC应用闲置后EF实体上下文异常:重启无效,改bin可恢复求助
.NET 4.8 MVC EF Code-First 偶发「实体类型不在当前上下文模型中」异常问题
问题现象
- .NET 4.8 MVC应用,采用EF Code-First实现(无EDMX文件、未使用迁移),本地及生产环境偶尔弹出错误:
The entity type <type> is not part of the model for the current context - 错误仅在应用闲置一段时间后触发,重启应用池、IIS甚至服务器都无法解决
- 临时修复有效:将bin文件夹重命名为bin-old,触发网站无bin目录的错误后改回原名,应用即可恢复正常,此前报错的实体类型不再出问题;重新发布应用也能解决
- 错误具有随机性,刷新页面后报错的实体类型会切换
可能原因
这类问题大概率是EF的模型元数据缓存与程序集加载状态不匹配导致的:
- 应用闲置期间,IIS可能回收应用程序域,程序集被卸载或重新加载,但EF的模型缓存没有同步更新,导致上下文无法识别实体类型
- 常规的重启应用池/IIS操作,可能没有彻底清除EF的模型缓存,而重命名bin的操作会强制触发应用程序域完全重建,让EF重新扫描程序集生成新的模型元数据
解决方案
临时应急方案
- 采用重命名bin文件夹再改回的方式快速恢复服务
- 直接重新发布应用,触发程序集重新加载与模型元数据重建
长期优化方案
- 规范DbContext生命周期管理:确保每个请求使用独立的DbContext实例,避免使用单例或静态上下文(比如在MVC中用依赖注入控制上下文的生命周期,每个请求创建一个实例)
- 显式指定实体程序集:在DbContext构造函数中强制指定EF扫描的实体所在程序集,避免自动扫描时出现异常:
public class YourDbContext : DbContext { public YourDbContext() : base("YourConnectionStringName") { this.Configuration.LazyLoadingEnabled = false; var modelBuilder = new DbModelBuilder(); // 替换为你的实体类型,指定所在程序集 modelBuilder.Configurations.AddFromAssembly(typeof(YourEntityType).Assembly); var model = modelBuilder.Build(this.Database.Connection); this.Database.Initialize(false); } // 声明DbSet public DbSet<YourEntityType> YourEntities { get; set; } } - 调整应用池回收策略:延长应用池闲置超时时间,减少因频繁回收导致的程序集加载异常
- 禁用EF模型缓存(排查用):在web.config中添加配置禁用模型缓存,验证是否为缓存问题(不推荐长期使用,会影响性能):
<appSettings> <add key="EntityFramework_ModelCachingEnabled" value="false" /> </appSettings>
堆栈追踪示例
[InvalidOperationException: The entity type [type] is not part of the model for the current context.] System.Data.Entity.Internal.InternalContext.UpdateEntitySetMappingsForType(Type entityType) +273 System.Data.Entity.Internal.InternalContext.GetEntitySetAndBaseTypeForType(Type entityType) +31 System.Data.Entity.Internal.Linq.InternalSet`1.Initialize() +69 System.Data.Entity.Internal.InternalEntityEntry..ctor(InternalContext internalContext, Object entity) +158 System.Data.Entity.DbContext.Entry(TEntity entity) +124
内容的提问来源于stack exchange,提问作者Scott Salyer
相关产品推荐
相关产品推荐

