实体框架核心可能是Web应用程序中的内存泄漏

时间:2018-02-27 23:21:06

标签: c# dependency-injection asp.net-core-mvc entity-framework-core

我在ASP.NET MVC Core(v1)应用程序中使用EF Core。我注意到在生产用于测试的应用程序时,IIS服务器通常会因为达到其内存限制而频繁地进行回收。

我想验证我在我的应用程序中使用dbContext的方式是否有效,并且在后台没有创建任何内存泄漏。我在SO上阅读了一些类似的帖子,人们建议在使用它之后处理上下文对象。

但我通过依赖注入使用它如下。

Startup.cs class snippet:

// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
    services.AddDbContext<Context>();
}

Context.cs class snippet:

    public class Context : IdentityDbContext<ApplicationUser> 
    {
        private IConfigurationRoot _config;
        private IHttpContextAccessor _HttpContextAccessor;

        public Context(IConfigurationRoot config, DbContextOptions options, IHttpContextAccessor HttpContextAccessor)
            : base(options)
        {
            _config = config;
            _HttpContextAccessor = HttpContextAccessor;
        }

        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) 
        {
            base.OnConfiguring(optionsBuilder);

            optionsBuilder.UseSqlServer(_config["ConnectionStrings:ContextConnection"]);
        }
}

services.AddDbContext<Context>是否会注入上下文的共享实例,这会导致随时间查询的所有实体的累积,从而占用内存?

编辑:我还有以下几个单例实例,如下所示:

services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();

services.AddSingleton<ILoggerService, LoggerService>();

services.AddSingleton<IEmailSender, EmailSender>();

谢谢!

1 个答案:

答案 0 :(得分:0)

在我的情况下,在动作过滤器和一些中间件中,我使用了一个通过services.BuildServiceProvider()创建的IServiceProvider,如下所示:

public class DependencyManager{
    static class IServiceProvider ServiceProvider{ get;set;}
}
public class SomeMiddleware{
    public void SomeMethod(){
         var someServiceInstance = DependencyManager.ServiceProvider.GetService<SomeService>();
    }
}

因此,为注入此服务而创建的所有作用域对象均未链接到任何请求,并且在请求结束时不会被处置。我通过在HttpContext下使用RequestServices修复了此问题:

public class SomeMiddleware{
    public void SomeMethod{
        var someServiceInstance = context.RequestServices.GetService<SomeService>()
    }
}