天天看點

Asp.Net頁面執行流程分析

請求一個頁面時首先被WWW服務截獲(inetinfo.exe程序),這個程序首先判斷頁面的字尾,然後根據IIS中的配置來決定調用哪個擴充程式,比如aspx的頁面就會調用c:\windows\microsoft.net\framework\v2.0.50727\aspnet_isapi.dll,aspnet_isapi.dll将請求發送給w3wp.exe程序(我們在調試IIS中網站時就是把VS2005附加到這個程序上的)。

接下來w3wp.exe程序就會調用.net類庫進行具體處理:

ISAPIRuntime-->HttpRuntime-->HttpApplicationFactory-->HttpApplication-->HttpModule--HttpHandlerFactory-->HttpHandler 這也是本文主要分析的地方。

下面隻是列出主要流程,如果喜歡鑽研的同學可以用Reflector去檢視

一:ISAPIRuntime

Asp.Net頁面執行流程分析

       bool useOOP = iWRType == 1;

Asp.Net頁面執行流程分析

        wr = ISAPIWorkerRequest.CreateWorkerRequest(ecb, useOOP);

Asp.Net頁面執行流程分析

        wr.Initialize();

Asp.Net頁面執行流程分析

        string appPathTranslated = wr.GetAppPathTranslated();

Asp.Net頁面執行流程分析

        string appDomainAppPathInternal = HttpRuntime.AppDomainAppPathInternal;

Asp.Net頁面執行流程分析

        if ((appDomainAppPathInternal == null) || StringUtil.EqualsIgnoreCase(appPathTranslated, appDomainAppPathInternal))

Asp.Net頁面執行流程分析

        {

Asp.Net頁面執行流程分析

            HttpRuntime.ProcessRequestNoDemand(wr);

Asp.Net頁面執行流程分析

            return 0;

Asp.Net頁面執行流程分析

        }

Asp.Net頁面執行流程分析

        HttpRuntime.ShutdownAppDomain(ApplicationShutdownReason.PhysicalApplicationPathChanged, SR.GetString("Hosting_Phys_Path_Changed", new object[] { appDomainAppPathInternal, appPathTranslated }));

Asp.Net頁面執行流程分析

        return 1;

Asp.Net頁面執行流程分析

它的主要作用是調用一些非托管代碼生成HttpWorkerRequest對象,該對象包含目前請求的所有資訊,然後傳遞給HttpRuntime,這裡生成的HttpWorkerRequest對象可以直接在我們的頁面中調用的,通過它取得原始的請求資訊:

Asp.Net頁面執行流程分析

            IServiceProvider provider = (IServiceProvider)HttpContext.Current;

Asp.Net頁面執行流程分析

            HttpWorkerRequest wr = (HttpWorkerRequest)provider.GetService(typeof(HttpWorkerRequest));

Asp.Net頁面執行流程分析

二:HttpRuntime

最主要的就是private void ProcessRequestInternal(HttpWorkerRequest wr)方法:

Asp.Net頁面執行流程分析

        context = new HttpContext(wr, false);

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

        IHttpHandler applicationInstance = HttpApplicationFactory.GetApplicationInstance(context);

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

  IHttpAsyncHandler handler2 = (IHttpAsyncHandler) applicationInstance;

Asp.Net頁面執行流程分析

  context.AsyncAppHandler = handler2;

Asp.Net頁面執行流程分析

  handler2.BeginProcessRequest(context, this._handlerCompletionCallback, context);

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

1、根據HttpWorkerRequest對象生成HttpContext,HttpContext應該大家都很熟悉的,它包含request、response等屬性,在頁面中經常會用到的;

2、調用HttpApplicationFactory來生成IHttpHandler(這裡生成的是一個預設的HttpApplication對象,HttpApplication也是IHttpHandler接口的一個實作)

3、調用HttpApplication對象執行請求

三:HttpApplicationFactory

正如2.2中所提    本文轉自永春部落格園部落格,原文連結:,如需轉載請自行聯系原作者到的,這裡主要是生成一個HttpApplication對象:

Asp.Net頁面執行流程分析

 internal static string GetApplicationFile()

Asp.Net頁面執行流程分析

 {

Asp.Net頁面執行流程分析

     return Path.Combine(HttpRuntime.AppDomainAppPathInternal, "global.asax");

Asp.Net頁面執行流程分析

 }

Asp.Net頁面執行流程分析

首先會檢視是否存在global.asax檔案,如果有的話就用它來生成HttpApplication對象,從這裡我們可以看到global.asax的檔案名是在asp.net的架構中寫死的,不能修改的。如果這個檔案不存在就使用預設的對象。

建立好HttpApplication之後對它進行初始化:

Asp.Net頁面執行流程分析

    application = (HttpApplication) HttpRuntime.CreateNonPublicInstance(this._theApplicationType);

Asp.Net頁面執行流程分析

 using (ApplicationImpersonationContext context2 = new ApplicationImpersonationContext())

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

     application.InitInternal(context, this._state, this._eventHandlerMethods);

Asp.Net頁面執行流程分析

 四、HttpApplication

這個是比較複雜也比較重要的一個對象

首先是執行初始化操作,比較重要的一步就是進行HttpModule的初始化:

Asp.Net頁面執行流程分析

        private void InitModules()

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

            this._moduleCollection = RuntimeConfig.GetAppConfig().HttpModules.CreateModules();

Asp.Net頁面執行流程分析

            this.InitModulesCommon();

Asp.Net頁面執行流程分析

它會讀取web.config中所有HttpModule的配置

在HookupEventHandlersForApplicationAndModules方法中綁定Module的事件處理程式接着進行事件實際綁定:

Asp.Net頁面執行流程分析

 if (HttpRuntime.UseIntegratedPipeline)

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

     this._stepManager = new PipelineStepManager(this);

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

 else

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

     this._stepManager = new ApplicationStepManager(this);

Asp.Net頁面執行流程分析
Asp.Net頁面執行流程分析

 this._stepManager.BuildSteps(this._resumeStepsWaitCallback);

在ApplicationStepManager的BuildSteps方法中可以看到事件的綁定執行順序:

Asp.Net頁面執行流程分析

app.CreateEventExecutionSteps(HttpApplication.EventBeginRequest, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventAuthenticateRequest, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventDefaultAuthentication, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostAuthenticateRequest, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventAuthorizeRequest, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostAuthorizeRequest, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventResolveRequestCache, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostResolveRequestCache, steps);

Asp.Net頁面執行流程分析

 steps.Add(new HttpApplication.MapHandlerExecutionStep(app));

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostMapRequestHandler, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventAcquireRequestState, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostAcquireRequestState, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPreRequestHandlerExecute, steps);

Asp.Net頁面執行流程分析

 steps.Add(new HttpApplication.CallHandlerExecutionStep(app));

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostRequestHandlerExecute, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventReleaseRequestState, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostReleaseRequestState, steps);

Asp.Net頁面執行流程分析

 steps.Add(new HttpApplication.CallFilterExecutionStep(app));

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventUpdateRequestCache, steps);

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventPostUpdateRequestCache, steps);

Asp.Net頁面執行流程分析

 this._endRequestStepIndex = steps.Count;

Asp.Net頁面執行流程分析

 app.CreateEventExecutionSteps(HttpApplication.EventEndRequest, steps);

Asp.Net頁面執行流程分析

 steps.Add(new HttpApplication.NoopExecutionStep());

Asp.Net頁面執行流程分析

注意上面紅色标注的MapHandlerExecutionStep(讀取所有的HttpHandler配置)、CallHandlerExecutionStep就是對Handle程式進行處理的,也就是說在web.config中配置的HttpHandler都是在這裡進行處理的,執行順序如上所示

然後就是調用2.3中的方法執行請求:

Asp.Net頁面執行流程分析

Code

在ResumeSteps中就是執行事件處理程式。  

五、HttpModule

在系統web.config中預設的配置有:

Asp.Net頁面執行流程分析

基本使用方法可以參見我的上一篇文章

六、HttpHandlerFactory、HttpHandler

這兩個對象在web.config中的配置方法是相同的,預設配置有:

Asp.Net頁面執行流程分析

要注意的是相同的字尾名配置多次的話,後面的配置會把前面的覆寫。

這裡我們重點看一下aspx的配置:System.Web.UI.PageHandlerFactory

這是一個HttpHandlerFactory對象,根據不同的Page生成不同的HttpHandler對象(我們自己的Page頁面都是一個IHttpHandler):

Asp.Net頁面執行流程分析

    Page page = BuildManager.CreateInstanceFromVirtualPath(virtualPath, typeof(Page), context, true, true) as Page;

Asp.Net頁面執行流程分析

    if (page == null)

Asp.Net頁面執行流程分析

    {

Asp.Net頁面執行流程分析

        return null;

Asp.Net頁面執行流程分析

    }

Asp.Net頁面執行流程分析

    page.TemplateControlVirtualPath = virtualPath;

Asp.Net頁面執行流程分析

    return page;

Asp.Net頁面執行流程分析

這裡會調用web.config中的buildProviders配置編譯頁面:

Asp.Net頁面執行流程分析

這樣就可以進入我們的Page執行了,大的執行順序可以參見第四部分的描述,它也就是一個HttpHandler.

    本文轉自永春部落格園部落格,原文連結:http://www.cnblogs.com/firstyi/archive/2008/05/08/1188545.html,如需轉載請自行聯系原作者

繼續閱讀