刚刚开始测试 EF6 及其异步功能。当我意识到它们不是线程安全的时,我很惊讶。我有点假设这就是重点。
多年来,我已经有了自己Task
的扩展方法,但我一直在等待 EF 使它们成为线程安全的。
至少我的基于任务的功能lock
不会相互干扰。EF6 甚至没有走那么远。但主要问题是我的代码与他们的代码共享。即尝试发出异步查询,然后在它完成之前尝试访问触发延迟加载的导航属性(在同一上下文中预加载的完全独立的实体上)。这可以由 UI 触发,也可以由即时函数之外的其他代码触发,或者由十几个其他场景触发。
据我所知。dbContext 中仅有的两个共享(实体之间)可变资源是连接和更改跟踪(缓存)。如果我们可以在这些功能周围添加锁定,那么我们将拥有一个线程安全的上下文。
我们甚至可以分两个阶段进行。如果我们可以实现一个提供者来锁定用于查询数据库的一个集中功能。然后,任何未跟踪的查询——无论是通过返回非实体(匿名)对象还是调用 AsNoTracking()——都是线程安全的,并且即使在另一个线程可能要求延迟加载的对象时也可以安全地使用 Async 函数调用。
我们的可扩展性不会比现在更糟,因为我们现在必须为每个线程使用一个上下文,如果您尝试跳过甚至一个 await 以引入一些并行性或在事件中工作,甚至 Async 函数也不在讨论范围内一旦等待的函数与任务一起返回,可能会触发系统(如 wpf)。
所以我的问题是。有没有人实现过这样的提供者。或者有人愿意和我一起工作吗?