0

我在一个 ASP.NET 应用程序中有大量的 AJAX 请求。

一旦用户登录我们的 Web 应用程序,就会创建一个会话来存储该用户状态的信息。目前,我们保持会话数据一致的解决方案非常简单和残酷:每个请求在被处理之前都需要获取一个独占锁

这适用于传统的 Web 应用程序。但是,当 Web 应用程序转而支持 AJAX 时,它变得不高效。很有可能多个 AJAX 请求同时发送到服务器而不重新加载网页。如果所有的 AJAX 请求都被排他锁序列化,那么响应就不会那么快了。无论如何,许多不访问相同会话变量的 AJAX 请求也会被阻止。

如果我们没有为每个请求设置独占锁,那么我们需要仔细处理所有竞争条件以避免死锁。恐怕这会使代码变得复杂和错误。

那么,是否有任何最佳实践来保持会话数据一致并保持代码简洁明了?

4

2 回答 2

1

我给你一个解决这个问题的总体思路。

使用Mutex,对于互斥体名称,使用会话 ID。

互斥锁基于您提供的名称,因此您可以避免会话之间的冲突。

一个简单的例子http://aspalliance.com/290

互斥与锁

这是一些答案
Monitor vs Mutex in c#

C# 中各种线程同步选项有什么区别?

在您的情况下,如果您使用会话 ID 作为 Mutex 名称,那么将使用此名称锁定。来自不同会话 id 的人不会被锁定,您只锁定来自相同会话 id 的相同人。

您描述了您的用户可以锁定所有用户,因此使用 Mutex(sessionid) 不会发生这种情况。

许多池,在同一台服务器中

如果您在同一台服务器上运行,互斥锁就很好。

许多网络服务器

如果你要同步不同的web服务器,你需要有一个通用的base,一个通用的数据库,或者一个可以读、写、锁等的通用目录。

对于公共目录:
在这种情况下,我不知道您是否可以使用 .\SharedDir\MutexSessionId1 之类的名称创建互斥锁,但如果您不能,那么您可以通过创建和锁定文件名自行创建类似的东西,之后你的工作完成了你删除它们,文件的锁就是你要求的锁。

对于通用数据库:
您可以创建一个可用于锁定和同步您的操作的表,使之类似于 mutex 所做的事情。

于 2010-04-03T15:40:11.973 回答
1

一旦用户登录我们的 Web 应用程序,就会创建一个会话来存储该用户状态的信息。目前,我们保持会话数据一致的解决方案非常简单和残酷:每个请求在被处理之前都需要获取排他锁”

我们的解决方案”意味着您没有使用 SessionStateModule 并使用自定义解决方案。在任何情况下,如果您使用 ASP.NET 提供的默认“会话”对象,它已经具有锁定功能,无需再次实现它。

ASP.net 提供了一个标记接口 IReadOnlySessionState 来指示特定请求只需要对会话进行读取访问(因此会话不会针对该特定请求锁定)。单击此处并导航到“并发请求和会话状态”部分以查找更多详细信息

现在,回答您的问题,将这个标记接口用于 AJAX 服务器端页面方法的方法是将 Page 的属性 EnableSessionState 设置为“ReadOnly”。

如果您使用的是 AJAX Pro,则可以在您的方法上使用 AjaxPro.AjaxMethod(HttpSessionRequirement.ReadOnly) 属性。

于 2010-04-04T11:55:28.797 回答