Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/333.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 尝试在请求管道内写入数据库时发生ObjectDisposedException_C#_Asp.net Core_.net Core - Fatal编程技术网

C# 尝试在请求管道内写入数据库时发生ObjectDisposedException

C# 尝试在请求管道内写入数据库时发生ObjectDisposedException,c#,asp.net-core,.net-core,C#,Asp.net Core,.net Core,我正在尝试添加一些代码,以便在每次请求时将DateTime值保存到数据库中 我添加了一些代码,用app.Use()配置方法 这是我的配置方法: public void Configure(IApplicationBuilder app, IHostingEnvironment env, MyDbContext db) { var appSettings = Configuration.GetSection("AppSettings").Get<AppSettin

我正在尝试添加一些代码,以便在每次请求时将DateTime值保存到数据库中

我添加了一些代码,用
app.Use()
配置方法

这是我的配置方法:

public void Configure(IApplicationBuilder app, IHostingEnvironment env, MyDbContext db)
{
    var appSettings = Configuration.GetSection("AppSettings").Get<AppSettings>();

    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }            

    app.UseCors(builder =>
       builder.WithOrigins(appSettings.BaseUrls.WebAllowCors)
              .AllowAnyHeader().AllowAnyMethod()
   );

    app.UseAuthentication();
    

    app.Use(async (context,next) =>
    {
        var id = context.User.Claims.First(x => x.Type == "sub").Value;

        var user = db.AspNetUsers.Find(id);

        user.LastAccessed = DateTime.Now;

        await db.SaveChangesAsync();

        await next();
    });

    app.UseMvc();
}
public void配置(IApplicationBuilder应用程序、IHostingEnvironment环境、MyDbContext数据库)
{
var appSettings=Configuration.GetSection(“appSettings”).Get();
if(env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}            
app.UseCors(builder=>
builder.WithOrigins(appSettings.BaseUrls.WebAllowCors)
.AllowAnyHeader().AllowAnyMethod()
);
app.UseAuthentication();
应用程序使用(异步(上下文,下一步)=>
{
var id=context.User.Claims.First(x=>x.Type==“sub”).Value;
var user=db.AspNetUsers.Find(id);
user.LastAccessed=DateTime.Now;
等待db.saveChangesSync();
等待下一个();
});
app.UseMvc();
}
但我得到了一个错误:

处理请求时发生未处理的异常

ObjectDisposedException:无法访问已处置的对象。此错误的一个常见原因是处理通过依赖项注入解析的上下文,然后在应用程序的其他位置尝试使用相同的上下文实例。如果对上下文调用Dispose(),或将上下文包装到using语句中,则可能会发生这种情况。如果您使用的是依赖项注入,那么应该让依赖项注入容器处理上下文实例。 对象名称:“MyDbContext”


在这里,对每个请求写入数据库的正确方法是什么?

可以有多种方法来处理这种情况。我将使用的一种方法是创建自定义过滤器,并使用自定义过滤器注释方法或操作,以更新用户的上次访问时间

public class UpdateLastAccessFilter : ActionFilterAttribute, IActionFilter
{
    void IActionFilter.OnActionExecuting(ActionExecutingContext filterContext)
    {
        // TODO: Add your action filter's tasks here

        // Log Action Filter call
        using (dbEntities context = new dbEntities())
        {

            var id = context.User.Claims.First(x => x.Type == "sub").Value;

        var user = db.AspNetUsers.Find(id);

        user.LastAccessed = DateTime.Now;

        await db.SaveChangesAsync();
            OnActionExecuting(filterContext);
        }
    }
}
[UpdateLastAccessFilter]
public class StoreController : Controller
{
    ...
}
然后修饰需要记录访问时间的方法或控制器

public class UpdateLastAccessFilter : ActionFilterAttribute, IActionFilter
{
    void IActionFilter.OnActionExecuting(ActionExecutingContext filterContext)
    {
        // TODO: Add your action filter's tasks here

        // Log Action Filter call
        using (dbEntities context = new dbEntities())
        {

            var id = context.User.Claims.First(x => x.Type == "sub").Value;

        var user = db.AspNetUsers.Find(id);

        user.LastAccessed = DateTime.Now;

        await db.SaveChangesAsync();
            OnActionExecuting(filterContext);
        }
    }
}
[UpdateLastAccessFilter]
public class StoreController : Controller
{
    ...
}

处理这种情况有多种方法。我将使用的一种方法是创建自定义过滤器,并使用自定义过滤器注释方法或操作,以更新用户的上次访问时间

public class UpdateLastAccessFilter : ActionFilterAttribute, IActionFilter
{
    void IActionFilter.OnActionExecuting(ActionExecutingContext filterContext)
    {
        // TODO: Add your action filter's tasks here

        // Log Action Filter call
        using (dbEntities context = new dbEntities())
        {

            var id = context.User.Claims.First(x => x.Type == "sub").Value;

        var user = db.AspNetUsers.Find(id);

        user.LastAccessed = DateTime.Now;

        await db.SaveChangesAsync();
            OnActionExecuting(filterContext);
        }
    }
}
[UpdateLastAccessFilter]
public class StoreController : Controller
{
    ...
}
然后修饰需要记录访问时间的方法或控制器

public class UpdateLastAccessFilter : ActionFilterAttribute, IActionFilter
{
    void IActionFilter.OnActionExecuting(ActionExecutingContext filterContext)
    {
        // TODO: Add your action filter's tasks here

        // Log Action Filter call
        using (dbEntities context = new dbEntities())
        {

            var id = context.User.Claims.First(x => x.Type == "sub").Value;

        var user = db.AspNetUsers.Find(id);

        user.LastAccessed = DateTime.Now;

        await db.SaveChangesAsync();
            OnActionExecuting(filterContext);
        }
    }
}
[UpdateLastAccessFilter]
public class StoreController : Controller
{
    ...
}

这可能是因为
MyDbContext
是一次性的,每次需要时都需要包装在using中

试试这个,看看它是否有效:

using (var context = db)
{
    context.AspNetUsers.Find(id);
}
您可能需要在以后使用
db
时执行相同的操作


我假设
MyDbContext
已在
StartUp.cs
ConfigureService(IServiceCollection服务)
功能中注册到IoC?大概是这样的:

services.AddDbContext<MyDbContext>(options =>
    options.UseSqlServer(Configuration.GetSection("ConnectionStrings:Sql").Value)
);
  app.Use(async (context, next) =>
        {
            var id = context.User.Claims.First(x => x.Type == "sub").Value;
            using(var db = context.RequestServices.GetService<MyDbContext>())
            {

               var user = db.AspNetUsers.Find(id);

               user.LastAccessed = DateTime.Now;

               await db.SaveChangesAsync();
            }
            await next();
        });
services.AddDbContext(选项=>
options.UseSqlServer(Configuration.GetSection(“ConnectionString:Sql”).Value)
);

这可能是因为
MyDbContext
是一次性的,每次需要时都需要包装在using中

试试这个,看看它是否有效:

using (var context = db)
{
    context.AspNetUsers.Find(id);
}
您可能需要在以后使用
db
时执行相同的操作


我假设
MyDbContext
已在
StartUp.cs
ConfigureService(IServiceCollection服务)
功能中注册到IoC?大概是这样的:

services.AddDbContext<MyDbContext>(options =>
    options.UseSqlServer(Configuration.GetSection("ConnectionStrings:Sql").Value)
);
  app.Use(async (context, next) =>
        {
            var id = context.User.Claims.First(x => x.Type == "sub").Value;
            using(var db = context.RequestServices.GetService<MyDbContext>())
            {

               var user = db.AspNetUsers.Find(id);

               user.LastAccessed = DateTime.Now;

               await db.SaveChangesAsync();
            }
            await next();
        });
services.AddDbContext(选项=>
options.UseSqlServer(Configuration.GetSection(“ConnectionString:Sql”).Value)
);

这可能是因为您使用的范围错误。 您正在从configure方法获取db实例。但这在启动时只调用一次

你应该这样做:

services.AddDbContext<MyDbContext>(options =>
    options.UseSqlServer(Configuration.GetSection("ConnectionStrings:Sql").Value)
);
  app.Use(async (context, next) =>
        {
            var id = context.User.Claims.First(x => x.Type == "sub").Value;
            using(var db = context.RequestServices.GetService<MyDbContext>())
            {

               var user = db.AspNetUsers.Find(id);

               user.LastAccessed = DateTime.Now;

               await db.SaveChangesAsync();
            }
            await next();
        });
app.Use(异步(上下文,下一步)=>
{
var id=context.User.Claims.First(x=>x.Type==“sub”).Value;
使用(var db=context.RequestServices.GetService())
{
var user=db.AspNetUsers.Find(id);
user.LastAccessed=DateTime.Now;
等待db.saveChangesSync();
}
等待下一个();
});

希望这个片段能帮助你。如果您需要任何澄清,我非常愿意回答您的问题。

这可能是因为您使用的范围错误。 您正在从configure方法获取db实例。但这在启动时只调用一次

你应该这样做:

services.AddDbContext<MyDbContext>(options =>
    options.UseSqlServer(Configuration.GetSection("ConnectionStrings:Sql").Value)
);
  app.Use(async (context, next) =>
        {
            var id = context.User.Claims.First(x => x.Type == "sub").Value;
            using(var db = context.RequestServices.GetService<MyDbContext>())
            {

               var user = db.AspNetUsers.Find(id);

               user.LastAccessed = DateTime.Now;

               await db.SaveChangesAsync();
            }
            await next();
        });
app.Use(异步(上下文,下一步)=>
{
var id=context.User.Claims.First(x=>x.Type==“sub”).Value;
使用(var db=context.RequestServices.GetService())
{
var user=db.AspNetUsers.Find(id);
user.LastAccessed=DateTime.Now;
等待db.saveChangesSync();
}
等待下一个();
});

希望这个片段能帮助你。如果您需要任何澄清,我将非常乐意回答您的问题。

哪一行引发异常?哪一行引发异常?我假设
MyDbContext
已在
StartUp.cs
配置服务(IServiceCollection服务)
功能中注册到IoC?类似这样的内容:
services.AddDbContext(options=>options.UseSql(Configuration.GetSection(“connectionString:Sql”).Value)
我假设
MyDbContext
已在
StartUp.cs
ConfigureService(iSeries收集服务)
功能中注册到IoC?类似这样的内容:
services.AddDbContext(options=>options.UseSql(Configuration.GetSection(“connectionString:Sql”).Value)谢谢,这解决了我的问题。Configure方法是配置管道,而不是实际的管道,因此当然上下文超出了我声明它的范围。事后看来,这是显而易见的。谢谢你的帮助!作为旁注,我不得不删除using语句,因为它在其他地方导致了相同的错误,因为它正在处理仍然需要的上下文