我在Efcore中阅读了很多关于DBcontext及其生命周期的文档和文章,但是,我有一些问题。
基于这个链接"https://learn.microsoft.com/en-us/ef/core/dbcontext-configuration/“,DBcontext的最佳生存期和AddDbContext的默认生存期是scope,但在本文档的以下两句话中存在矛盾。
"DbContext不是线程安全的。不要在线程之间共享上下文。在继续使用上下文实例之前,一定要等待所有异步调用。“
另一方面,也有人提到,
“在大多数核心应用程序中,安全地避免并发访问问题,因为在给定的时间只有一个线程执行每个客户端请求,而且因为每个请求都有一个单独的依赖项注入作用域(因此也是一个单独的DbContext实例)。”
此外,我还阅读了一些禁止注册singleton DbContext的文档,但是AddDbContextPool进行了单例DBcontext的注册。所以有一些关于Dbcontextpool的问题。
发布于 2022-04-11 12:34:00
我理解您为什么认为Microsoft文档中的语言令人困惑。我会帮你解开的:
AddDbContext<T>()
,ASP.NET核心确保每个请求都有自己的DbContext
实例,因此默认情况下使其“不受并发访问的影响”)。1我对将DBcontext注册为作用域服务是否是线程安全感到困惑?
DbContext实例本身并不是线程安全的,这就是为什么您应该将它们注册为Scoped
,因为这将防止从多个请求访问它们,从而使它们的使用线程安全。
2详细地将DBcontext注册为单例服务有哪些问题?
在这个答案中已经详细描述了这一点,您已经引用了这些内容。我想这个答案有很多细节,我不想在这里重复。
此外,我还阅读了一些禁止注册单例DbContext的文档,然而,AddDbContextPool制作了注册单例DBcontext。所以有一些关于Dbcontextpool的问题。
DbContext池特性与将DbContext注册为单例非常不同,因为:
使用DbContextPool而不是DbContext有什么影响?
有关这方面的更多信息,请在这文档中提供。
什么时候我们应该使用它,当我们使用contextPool时应该考虑什么?
当您的应用程序需要它带来的性能好处时。在决定添加之前,您可能需要对其进行基准测试。
DbContextPool是线程安全吗?
是的,就像注册一个DbContext是线程安全的Scoped
一样;如果您意外地将一个DbContext实例保存在一个可重用的交叉请求对象中,这个保证就被破坏了。您必须很好地照顾Scoped
对象,以防止它们成为俘虏属地。
是否因为在应用程序的整个生命周期中存储了许多dbset实例而导致内存问题?
记忆的损失是很难被察觉的。对于在请求结束后被带回池的每个DbContext,都会清除所谓的第一级缓存。这是为了防止DbContext变得陈旧,并防止内存问题。
更改跟踪或ef的任何部分是否在DB上下文池中失败?
不,它没有。在大多数情况下,使您的DbContext池只需要基础设施更改(更改应用程序的启动路径),并且对应用程序的其他部分是透明的。但是,请务必阅读这,以熟悉使用DbContext池的后果。
https://stackoverflow.com/questions/71825752
复制相似问题