【发布时间】:2022-01-24 07:57:15
【问题描述】:
我有这样的代码:
private async void GetCommonInfo(HttpResponse res, MyDbContext db)
{
long lastUpdated = await db.InfoUpdated.Select(r => r.Common).FirstOrDefaultAsync();
var info = new CommonInfo
{
ARows = await QueryTool.AllIndexByID(db.TableA),
BRows = await QueryTool.AllIndexByID(db.TableB),
CRows = await QueryTool.AllIndexByID(db.TableC),
LastUpdated = lastUpdated,
};
await res.WriteAsJsonAsync(info);
}
同时:
public class QueryTool
{
public static async Task<Dictionary<int, T>> AllIndexByID<T>(DbSet<T> dbSet)
where T : class, ITableModel
{
return (await dbSet.AsNoTracking().ToListAsync()).ToDictionary(b => b.ID, b => b);
}
}
当我调用这个方法时,我得到了这个异常:
fail: Microsoft.EntityFrameworkCore.Query[10100]
An exception occurred while iterating over the results of a query for context type 'ApiServer.Models.MyDbContext'.
System.ObjectDisposedException: Cannot access a disposed context instance. A common cause of this error is disposing a context instance that was resolved from dependency injection and then later trying to use the same context instance elsewhere in your application. This may occur if you are calling 'Dispose' on the context instance, or wrapping it in a using statement. If you are using dependency injection, you should let the dependency injection container take care of disposing context instances.
Object name: 'MyDbContext'.
at Microsoft.EntityFrameworkCore.DbContext.CheckDisposed()
at Microsoft.EntityFrameworkCore.DbContext.get_DbContextDependencies()
at Microsoft.EntityFrameworkCore.DbContext.Microsoft.EntityFrameworkCore.Internal.IDbContextDependencies.get_StateManager()
at Microsoft.EntityFrameworkCore.Query.QueryContextDependencies.get_StateManager()
at Microsoft.EntityFrameworkCore.Query.QueryContext.InitializeStateManager(Boolean standAlone)
at Microsoft.EntityFrameworkCore.Query.Internal.SingleQueryingEnumerable`1.AsyncEnumerator.InitializeReaderAsync(AsyncEnumerator enumerator, CancellationToken cancellationToken)
at Pomelo.EntityFrameworkCore.MySql.Storage.Internal.MySqlExecutionStrategy.ExecuteAsync[TState,TResult](TState state, Func`4 operation, Func`4 verifySucceeded, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Query.Internal.SingleQueryingEnumerable`1.AsyncEnumerator.MoveNextAsync()
看起来注入DbContext的依赖只能用于一个查询,然后将其释放。
如果可以的话,我该如何通过喜欢、使用同步方法或将四个查询集成到一个查询中来解决这个问题,不使用依赖注入或其他方式?
【问题讨论】:
-
您的问题是
async void。替换为async Task,别忘了等待GetCommonInfo -
哦是的。你会发布答案以便我接受吗?
-
EF Core 处理实体,而不是表。服务器在大表中搜索单个记录的速度也比任何字典快得多——它有更多的 RAM、更多的 CPU 内核和更智能的索引算法。如果您只想加载查找表,使用 Dapper 会更简单,无需配置 DbContext 和未使用的关系
-
在我的情况下,这些表将用于其他 API。
标签: c# mysql entity-framework-core