IRequiresSessionState与IReadOnlySessionState的区别

26
除了第二个接口无法保存会话变量之外,IRequiresSessionStateIReadOnlySessionState之间有什么区别呢?
两者都允许我在HttpHandler中访问会话变量。 但是为什么我会更喜欢使用IReadOnlySessionState?它只是限制了我不能保存会话以供下一个请求使用。
或者它能给我比IRequiresSessionState更好的性能表现吗?
什么时候我会更喜欢使用IReadOnlySessionState而不是IRequiresSessionState
3个回答

29
一项关键的区别在于IRequiresSessionState对当前会话进行了独占锁定,从而可能限制当前用户的并发请求数量。(有关此锁定现象的更多背景信息,请参见在使用ASP.NET会话时是否可能强制请求并发处理?
相比之下,IReadOnlySessionState不会获取独占锁定。
这与renad's helpful answer to an almost identical SO question中记录的内容相同。
我找到的最好的官方文档是来自MSDN文章Session State Providers
在会话状态提供程序中,最重要的三种方法是GetItem、GetItemExclusive和SetAndReleaseItemExclusive。前两个方法由SessionStateModule调用以从数据源检索会话。如果请求的页面实现了IRequiresSessionState接口(默认情况下,所有页面都实现了IRequiresSessionState),SessionStateModule的AcquireRequestState事件处理程序将调用会话状态提供程序的GetItemExclusive方法。方法名称中的“Exclusive”表示仅在另一个请求未使用该会话时才检索会话。另一方面,如果请求的页面实现了IReadOnlySessionState接口(最常见的方法是在页面的@ Page指令中包含EnableSessionState =“ReadOnly”属性),则SessionStateModule调用提供程序的GetItem方法。这里不需要排他性,因为SessionStateModule允许重叠读访问。
请注意,显式使用这些接口和使用EnableSessionState页面指令之间的对应关系。
  • EnableSessionState=False <-> 没有I*SessionState接口
  • EnableSessionState=True <-> IRequiresSessionState接口
  • EnableSessionState=ReadOnly <-> IReadOnlySessionState接口

3
+1锁定 - 如果Web应用程序可能同时处理使用会话状态的少量异步请求,则非常重要。 - Tim M.

7
那个接口控制框架是否在请求结束时保存当前会话状态。当您使用外部进程的会话状态存储时,它会产生更大的影响。在这种情况下,如果没有该接口,即使会话数据没有更改(系统不跟踪请求期间是否修改了会话数据),系统仍将在远程数据库中存储会话数据。当您使用IReadOnlySessionState接口时,写回阶段被跳过。

2
你从哪里得到这个信息的?你能提供链接吗? - Royi Namir

1

是的,我知道IRequiresSessionState是用来做什么的,但为什么还存在IReadOnlySessionState呢?为什么我会更倾向于使用它呢? - Oleg Grishko
在PostMapRequestHandler中,HttpModule从实际处理程序切换到实现IRequiresSessionState或IReadOnlySessionState的自定义处理程序,以便可以使用会话。 在PreRequestHandlerExecute中,您可以访问会话并在需要时重定向。 在PostAcquireRequestState中,您将切换回原始处理程序。 - coder

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接