Wednesday, October 26, 2011

Measure your site performance (HTTPModule)

Preface

When creating a web site or web service , often you wonder how to measure request life cycle. May be you wonder if requested or web service ended at all. In order to do it we will look in feature that .Net framework expose to us, "HTTPModule"  .

HTTPModule

So what is HTTPModule ?  Picture for example water filter.  When water flowing from the crane , it's coming to some filter , filter doing some stuff with it ,and it's coming to your glass. The same mechanism is with the "HTTP" module . When you are requesting some page, you can write you own filter that will be invoked before beginning processing the page. And will pass page to parser that will process Asp. page.

Implementation

In order to implement filter we need to create a new class that will inherit from IHttpModule interface.
Than we need to implement Init function of the interface . Please see example


  public void Init(HttpApplication httpApplication)
        {
            
            // register for events created by the pipeline 
            httpApplication.BeginRequest += new EventHandler(this.OnBeginRequest);
            httpApplication.EndRequest += new EventHandler(this.OnEndRequest);
        }

When implementing the Init function we will subscribe to HTTPApplication events.
Like in the example below we subscribed to Begin and End  Request.

So when we will request specific page before process the page we will enter
to OnBeginRequest function . After the request ended  OnEndRequest function
will be called.

See all various events that we can subscribe to


  • AcquireRequestState:  event will be called to allow the module to acquire or create the state (for example, session) for the request.
  • AuthenticateRequest:  event will be called when a security module needs to authenticate the user before it processes the request.
  • AuthorizeRequest: event will be called  by a security module when the request needs to be authorized. Called after authentication.
  • BeginRequest: event will be called  to notify a module that new request is beginning.
  • Disposed: event will be called to notify the module that the application is ending for some reason. Allows the module to perform internal cleanup.
  • EndRequest: event will be called to notify the module that the request is ending.
  • Error: event will be called  to notify the module of an error that occurs during request processing.
  • PostRequestHandlerExecute: event will be called  to notify the module that the handler has finished processing the request.
  • PreRequestHandlerExecute: event will be called  to notify the module that the handler for the request is about to be called.
  • PreSendRequestContent: event will be called  to notify the module that content is about to be sent to the client.
  • PreSendRequestHeaders: Call this event to notify the module that the HTTP headers are about to be sent to the client.
  • ReleaseRequestState: Call this event to allow the module to release state because the handler has finished processing the request.
  • ResolveRequestCache: event will be called  after authentication. Caching modules use this event to determine if the request should be processed by its cache or if a handler should process the request.
  • UpdateRequestCache: event will be called  after a response from the handler. Caching modules should update their cache with the response.
In our example we subscribed only to Begin and End Request. See the event handler functions

 public void OnBeginRequest(object o, EventArgs args)
        {
            beginrequest = DateTime.Now;
            Trace.Write(string.Format("Request started at {0}", DateTime.Now));
        }
        public void OnEndRequest(object obj, EventArgs args)
        {
            // get the time elapsed for the request 
            TimeSpan elapsedtime = DateTime.Now - beginrequest;
            Trace.Write(string.Format("Request ended at {0}", DateTime.Now));
            Trace.Write(string.Format("Elapsed time {0}", elapsedtime));
        }

And final step , we need to declare about our model in web config . In order 
to declare need to add following row 
      <add name="RequestInspector" type="Namespace.Class,Assembly"/>

Please see example below
  <system.web>
    <httpModules>
      <add name="RequestInspector" type="RequestInspectorNamespace.RequestInspector,RequestInspectorAssembly"/>
    </httpModules>


You can download  Source Code