【问题标题】:ObjectDisposedException on DbContextDbContext 上的 ObjectDisposedException
【发布时间】:2020-09-23 09:16:54
【问题描述】:

当使用DbContext 从另一个服务注入到一个服务时,我收到以下错误:

ObjectDisposedException: Cannot access a disposed object.

我的DbContext 的生命周期是Scoped,我的服务的生命周期是Transient,但是将这些更改为Singleton(我们不想要)并不能解决问题。

有趣的是,错误似乎是随机发生的。有时没有错误,一切运行良好。

关于这个错误,当我的 Angular 应用程序开始向后端发出请求时,我(也是随机地)在启动后立即收到 InvalidOperationException
"An attempt was made to use the context while it is being configured. A DbContext instance cannot be used inside OnConfiguring since it is still being configured at this point."

我的代码:

public class MyService1 {

    private static IMyService2 _myService2;

    public MyService1(IMyService2 myService2){
        _myService2 = myService2;
    }

    public async Task DoSomethingWithMyService2() {
        await _myService2.DoSomething(new MyEntity());
    }
}
public class MyService2 : IMyService2 {

    private MyDbContext _dbContext;

    public MyService2(MyDbContext myDbContext) {
        _dbContext = myDbContext;
    }

    public async Task DoSomething(MyEntity myEntity) {
        await _dbContext.MySet.AddAsync(myEntity); // <-- ObjectDisposedException
        await _dbContext.SaveChangesAsync();
    }
}

【问题讨论】:

    标签: asp.net-core entity-framework-core dbcontext asp.net-core-2.1


    【解决方案1】:

    回答我自己的问题:罪魁祸首是MyService2 在注入MyService1 后存储在static 字段中。

    因为DbContext 的生命周期是Scoped,所以它将在对服务的初始请求后被释放。但是,该服务将在整个应用程序的生命周期内继续存在,并引用其处置的 DbContext。

    (我不完全确定后者(关于应用程序的生命周期),因为MyService1 本身也是Transient。也许其他人可以解释它是如何工作的。)

    【讨论】:

    • this page 上描述了生命周期。 Transient 表示每次注入时都会创建一个新实例。
    • 谢谢。我的意思是我不确定静态字段在瞬态服务中的行为方式。通常一个静态类会在应用程序启动时创建一次(对吗?),但我想一个类中的一个字段的工作方式不同?
    • many questions 关于静态字段的生命周期,但是依赖注入机制的目标之一是消除对静态对象的需求,因为您可以简单地注入所有依赖项在构造函数中,不需要知道它们来自哪里。您是否有理由需要 S2 的静态字段?
    • 没有任何原因,除了 The Previous Guy 是这样写的,我在调试异常时忽略了它。
    猜你喜欢
    • 1970-01-01
    • 2018-03-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-05-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多