【发布时间】:2020-11-06 14:50:33
【问题描述】:
我有一个小问题,我一直在使用页面上的视图组件,但我一直遇到以下问题。我正在使用 asp.net core 3.1 和 ef core 3.1
处理请求时数据库操作失败。 InvalidOperationException:在此上下文中启动了第二个操作 在之前的操作完成之前。这通常是由 不同的线程使用相同的 DbContext 实例。更多 有关如何避免 DbContext 线程问题的信息,请参阅 https://go.microsoft.com/fwlink/?linkid=2097913。有待处理 MISDBContext 的模型更改在 Visual Studio 中,使用 Package 管理器控制台为这些更改构建新的迁移,并 将它们应用于数据库:
PM> Add-Migration [迁移名称] PM> Update-Database 或者, 您可以搭建一个新的迁移并从命令提示符处应用它 你的项目目录:
dotnet ef 迁移添加 [迁移名称] dotnet ef 数据库更新
我已经检查了 SO,它建议您现在将以下内容添加到您的课程中,我认为我根本不需要第二个上下文是正确的,这是导致我的问题的原因。我加了一行
ServiceLifetime.Transient
显然,以上行允许更多并发连接到上下文。
services.AddDbContext<MISDBContext>
(options => options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")), ServiceLifetime.Transient);
services.AddDbContext<ApplicationDbContext>(options =>
options.UseSqlServer(
Configuration.GetConnectionString("DefaultConnection")), ServiceLifetime.Transient);
这是我的视图组件的典型布局,我认为实际上它可能是导致问题的原因,因为我试图在访问上下文的同时访问用户存储。
private Task<ApplicationUser> GetCurrentUserAsync() => _userManager.GetUserAsync(HttpContext.User);
public async Task<Guid> GetCurrentTennantId() {
ApplicationUser usr = await GetCurrentUserAsync();
TempData["TeannantId"] = usr?.Id;
Guid.TryParse(usr?.Id, out Guid resultTennantId);
return resultTennantId;
}
private Task<List<ApplicationUser>> GetItemsAsync() {
string currentUser = GetCurrentTennantId().Result.ToString();
var excludeCurrentUser= _userManager.Users.Where(w => w.Id != currentUser).ToListAsync();
return excludeCurrentUser;
}
}
【问题讨论】:
-
_userManager使用哪个 DbContext?您是否同时使用两个 dbContexts?另外,您真的需要两个 dbContext 用于同一个数据库吗?一些有趣的阅读here。 -
它使用 MISDBContext 是我删除有问题的问题的问题。
-
在我看来,要解决这个问题,您应该确保在调用 GetCurrentUserAsync 和 GetCurrentTennantId 方法时始终立即等待异步调用。
标签: c# entity-framework asp.net-core