【发布时间】:2012-07-06 21:02:25
【问题描述】:
This commentStephen Cleary 这么说:
AspNetSynchronizationContext是最奇怪的实现。它将Post视为同步而非异步,并且使用锁一次执行一个委托。
同样,the article that he wrote on synchronization contexts 并在该评论中链接到:
从概念上讲,AspNetSynchronizationContext 的上下文是复杂的。在异步页面的生命周期中,上下文仅从 ASP.NET 线程池中的一个线程开始。异步请求启动后,上下文不包含任何线程。当异步请求完成时,执行其完成例程的线程池线程进入上下文。这些可能是发起请求的线程,但更有可能是操作完成时恰好空闲的线程。
如果多个操作一次完成同一个应用程序,AspNetSynchronizationContext 将确保它们一次执行一个。它们可以在任何线程上执行,但该线程将具有原始页面的标识和文化。
挖掘反射器似乎可以验证这一点,因为它在调用任何回调时会锁定HttpApplication。
锁定应用对象似乎很可怕。所以我的第一个问题:这是否意味着今天,整个应用程序的所有异步完成都一次执行一个,即使是源自具有单独 HttpContexts 的单独线程上的单独请求的那些?对于任何 100% 使用异步页面(或 MVC 中的异步控制器)的应用程序来说,这不是一个巨大的瓶颈吗?如果不是,为什么不呢?我错过了什么?
此外,在 .NET 4.5 中,似乎有一个新的 AspNetSynchronizationContext,旧的重命名为 LegacyAspNetSynchronizationContext,并且仅在未设置新的应用程序设置 UseTaskFriendlySynchronizationContext 时使用。所以问题 #2:新的实现会改变这种行为吗?否则,我想随着新的 async/await 支持通过同步上下文封送完成,这种瓶颈会更频繁地被注意到。
this forum post 的答案(从 SO 答案here 链接)表明这里发生了根本性的变化,但我想弄清楚那是什么以及哪些行为得到了改进,因为我们有一个 .NET 4 MVC 3几乎 100% 异步操作方法调用 Web 服务的应用程序。
【问题讨论】:
-
我怀疑现有行为被认为“足够好”。请记住,异步操作本身是独立的;只有它们的完成例程(和延续)是同步的。此外,异步页面在 4.5 之前很难;目前大多数 ASP.NET 应用程序都是同步的。
-
而且我还没有机会查看新的 ASP.NET 同步上下文。事实上,上周末刚刚安装了 VS2012RC 的 4.5!但如果没有其他人,我最终会在这里回答。
-
请做。您将成为该主题最权威的消息来源之一。
标签: asp.net asp.net-mvc multithreading asynchronous async-await