• 设为首页
  • 点击收藏
  • 手机版
    手机扫一扫访问
    迪恩网络手机版
  • 关注官方公众号
    微信扫一扫关注
    公众号

ASP.NET中Session实现原理浅析[1]会话的建立流程

原作者: [db:作者] 来自: [db:来源] 收藏 邀请
    HTTP 协议之所以能够获得如此大的成功,其设计实现的简洁性和无状态连接的高效率是很重要的原因。而为了在无状态的 HTTP 请求和有状态的客户端操作之间达到平衡,产生了服务器端会话 (Session) 的概念。客户端在连接到服务器后,就由 Web 服务器产生并维护一个客户端的会话;当客户端通过无状态 HTTP 协议再次连接到服务器时,服务器根据客户端提交的某种凭据,如 Cookie 或 URL 参数,将客户关联到某个会话上。这种思路在各种开发语言和开发环境中大量得到应用。
    在 ASP.NET 中,Web 应用程序和会话状态被分别进行维护,通过 HttpApplication 和 HttpSessionState 分离 Web 应用程序与会话的功能。应用程序层逻辑在 Global.asax 文件中实现,运行时编译成 System.Web.HttpApplication 的实例;会话则作为单独的 System.Web.SessionState.HttpSessionState 实例,由服务器统一为每个用户会话维护,通过 ASP.NET 页面编译成的 System.Web.UI.Page 对象子类的 Session 属性访问。关于 ASP.NET 中不同层次关系可参考我以前的一篇文章《.NET 1.1中预编译ASP.NET页面实现原理浅析 [1] 自动预编译机制浅析》,以下简称【文1】。

    ASP.NET 在处理客户端请求时,首先将根据客户端环境,生成一个 System.Web.HttpContext 对象,并将此对象作为执行上下文传递给后面的页面执行代码。
    在【文1】的分析中我们可以看到,HttpRuntime 在处理页面请求之前,根据 HttpWorkerRequest 中给出的环境,构造 HttpContext 对象,并以次对象作为参数从应用程序池中获取可用应用程序。简要代码如下:
private void HttpRuntime.ProcessRequestInternal(HttpWorkerRequest wr)


    HttpApplicationFactory 工厂内部维护了一个可用的应用程序实例缓冲池,用户降低应用程序对象构造的负荷。
    如果池中没有可用的应用程序对象实例,此对象工厂最终会调用 System.Web.HttpRuntime.CreateNonPublicInstance 方法构造新的应用程序实例,并调用其 InitInternal 方法初始化。详细步骤分析见【文1】
internal static IHttpHandler HttpApplicationFactory.GetApplicationInstance(HttpContext ctxt)

    这里的 System.Web.HttpApplication.InitInternal 函数完成对应用程序对象的初始化工作,包括调用 HttpApplication.InitModules 函数初始化 HTTP 模块(后面将详细介绍),并将作为参数传入的 HttpContext 实例保存到 HttpApplication._context 字段中。而此 HTTP 上下文对象将被后面用于获取会话对象。
public class HttpApplication : 

    而在 ASP.NET 页面中获取会话的方法也是类似,都是通过 HttpContext 来完成的。
public class Page : 

    在 HttpContext 中,实际上是通过一个哈希表保存诸如会话对象之类信息的
public sealed class HttpContext : 

    而 HttpContext.Session 所访问的又是哪儿来的呢?这就又需要回到我们前面提及的 HttpApplication.InitModules 函数。

    在 .NET 安装目录 Config 子目录下的 machine.config 定义了全局性的配置信息,而 HttpApplication 就是使用其中 system.web 一节的配置信息进行初始化的。
<system.web>
    
<httpModules>
      
<add name="OutputCache" type="System.Web.Caching.OutputCacheModule" />
      
<add name="Session" type="System.Web.SessionState.SessionStateModule" />
      
<add name="WindowsAuthentication" type="System.Web.Security.WindowsAuthenticationModule" />
      
<add name="FormsAuthentication" type="System.Web.Security.FormsAuthenticationModule" />
      
<add name="PassportAuthentication" type="System.Web.Security.PassportAuthenticationModule" />
      
<add name="UrlAuthorization" type="System.Web.Security.UrlAuthorizationModule" />
      
<add name="FileAuthorization" type="System.Web.Security.FileAuthorizationModule" />
      
<add name="ErrorHandlerModule" type="System.Web.Mobile.ErrorHandlerModule, System.Web.Mobile, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />
    
</httpModules>
</system.web>

    httpModules 节点指定了 HttpApplication 需要初始化的模块列表,而在前面提到的 HttpApplication.InitModules 函数正式根据此列表进行初始化的
private void HttpApplication.InitModules()

    Session 节点对于的 System.Web.SessionState.
<system.web>
    
<sessionState mode="InProc"
                  stateConnectionString
="tcpip=127.0.0.1:42424"
                  stateNetworkTimeout
="10"
                  sqlConnectionString
="data source=127.0.0.1;Integrated Security=SSPI"
                  cookieless
="false"
                  timeout
="20" />
</system.web>

    sessionState 的使用方法请参加 MSDN 中相关介绍和 INFO: ASP.NET State Management Overview。关于不同 mode 的会话管理的话题我们后面再讨论,先继续来看会话的建立过程。

    在从 machine.config 文件中读取配置信息后,InitModuleFromConfig 方法会向 HttpApplication 实例注册几个会话管理事件处理函数,负责在应用程序合适的情况下维护会话状态。
private void SessionStateModule.InitModuleFromConfig(HttpApplication app,
    SessionStateSectionHandler.Config config, 
bool configInit)

    BeginAcquireState 和 EndAcquireState 作为一个异步处理器注册到 HttpApplication._acquireRequestStateEventHandlerAsync 字段上;OnReleaseState 则负责在合适的时候清理会话状态;OnEndRequest 则是 OnReleaseState 的一个包装,负责较为复杂的请求结束处理。前面提到的 HttpApplication.InitInternal 函数,在完成了初始化工作后,会将上述这些事件处理器,加入到一个执行队列中,由应用程序在合适的时候,使用流水线机制进行调用,最大化处理效率。有关 ASP.NET 中流水线事件模型的相关介绍,请参考 HTTP PIPELINES
Securely Implement Request Processing, Filtering, and Content Redirection with HTTP Pipelines in ASP.NET
 一文中 The Pipeline Event Model 小节,有机会我在写文章详细分析。

    知道了会话建立的调用流程再来看会话的实现就比较简单了,
    至此,ASP.NET 中的会话建立流程大概就分析完毕了,下一小节将进一步展开分析多种不同会话管理器的实现原理与应用。

鲜花

握手

雷人

路过

鸡蛋
该文章已有0人参与评论

请发表评论

全部评论

专题导读
热门推荐
热门话题
阅读排行榜

扫描微信二维码

查看手机版网站

随时了解更新最新资讯

139-2527-9053

在线客服(服务时间 9:00~18:00)

在线QQ客服
地址:深圳市南山区西丽大学城创智工业园
电邮:jeky_zhao#qq.com
移动电话:139-2527-9053

Powered by 互联科技 X3.4© 2001-2213 极客世界.|Sitemap