16.6. After Deployment

The application has been developed and tested, the predeployment checklist has been satisfied, and deployment is completed. Now it's time to keep an eye on things and consider what changes might be necessary with the application running in the real world. You will need to monitor performance counters and consider other configuration changes to satisfy production demands.

16.6.1. Performance Monitoring

As you monitor the performance of a deployed ASP.NET application, it is key to understand that performance is really a complex balancing act. Incoming requests can be handled very quickly if the content is cached. However, caching content increases the memory consumption and can put additional pressure on the system to page memory to disk. And caching implies that the output sent for any single request is only as accurate or up to date as when it went into the cache. Some content that is customized based on unique user input may not be cacheable and may truly require that dynamic results be produced. This becomes even more complex when you add that the application is running in a garbage-collected environment that is periodically preempting other work in order to clean up unused memory and add and remove worker threads in a self-tuning effort.

You can gather some data from Windows performance counters on the server in order to monitor how it is running, using the Perfmon tool that comes with Windows. Don't focus entirely on a single performance metric. In a balancing act, different components must be considered. You can find an excellent article, "ASP.NET Performance Monitoring, and When to Alert Administrators," by Thomas Marquardt of the ASP.NET team on the MSDN site at http://msdn2.microsoft.com/en-us/library/ms972959.aspx. Marquardt recommends a specific set of performance counters as the minimum set to watch. Among other counters, his list includes:

  • Processor(_Total)\% Processor Time and Process(aspnet_wp)\% Processor Time: If the total processor time is consistently high and the ASP.NET worker process isn't responsible, the Web application may be getting starved for processing power because of other things happening on the machine. If the worker process time is consistently high, it may indicate that you are hitting the limit of the load the machine can handle.

  • Process(aspnet_wp)Private Bytes: The private bytes counter indicates how much memory the process has committed. A steady increase is a good indicator that something in the application is allocating resources that aren't being returned to the system. This will lead to problems of process recycling and should be investigated.

  • Process(aspnet_wp)Virtual Bytes: The virtual bytes correspond to the virtual address space the process has consumed. As this approaches the limit of 2GB (or optionally 3GB in 64-bit environments when it is enabled), it indicates that the address space is becoming fragmented. Items held in a cache may still be pinned, while other memory used transiently is been returned. Just as defragmenting your hard drive can improve performance, so can defragmenting the address space of the worker process. However, there isn't a great way to do this now, so the solution is to recycle the worker process. ASP.NET will do this for you automatically. The threshold at which this happens is configured as the Maximum Virtual Memory setting, found in the Internet Services Manager on the Recycling tab for the Application Pool.

  • ASP.NETApplication Restarts: Application restarts incur a cost of compilation checks and starting from scratch in populating the cache. Keep an eye out for excessive application restarts that can be caused by tools touching key files such as machine.config or web.config. This problem is known to be a side effect of some virus-scanning tools.

  • ASP.NETRequests Rejected: Rejected requests are bad. The server refused to deliver a page to someone trying to access the Web application. When requests queued and requests executing exceed a limit, ASP.NET will start rejecting requests in order to catch up.

Monitoring this small set of performance counters can give you insight into how healthy the application is after it has been deployed and can alert you to problems. Several commercial tools are available that will monitor performance counters and can be configured to send mail, page you, or even call you when thresholds are exceeded. The sophistication of monitoring suites continues to improve as the approaches to making the most of the ASP.NET runtime are refined.

16.6.2. Controlling AJAX Features

The system.web.extensions section itself is essentially all commented out except for the structure definition. When deploying an application, it is important to understand what default behaviors are controlled by configuration and ensure that the actual values correspond to your intentions.

By default, the JSON serializer of ASP.NET limits the length of JSON strings that it will consume. If the incoming data exceeds the limit, an exception is thrown. This is done to guard against wasting processing power on excessively long strings that may be created by someone to attack a server. The jsonSerialization section lets you customize the limit on JSON strings that will be processed. It can also accept a definition of custom converters for serializing and deserializing additional types:

<system.web.extensions>
 <scripting>
  <webServices>
<! --  Uncomment this line to customize maxJsonLength and add a custom converter  -- >
  <! --
  <jsonSerialization maxJsonLength="102400">
   <converters>
    <add name="ConvertMe" type="Acme.SubAcme.ConvertMeTypeConverter"/>
   </converters>
  </jsonSerialization>
   -- >

Script access to the ASP.NET application services is not enabled by default; you must turn them on explicitly. The authentication service can be configured to reject requests that aren't using SSL for security. The profile service must be enabled if you want to use it. You also have to define what properties are available for reading or writing remotely from script:

<! --
 <authenticationService enabled="true" requireSSL = "true|false"/>
 -- >
 <! --
 <profileService enabled="true"
         readAccessProperties="propertyname1,propertyname2"
         writeAccessProperties="propertyname1,propertyname2" />
 -- >
 </webServices>

The Roles Service was not available in the original ASP.NET AJAX release and is not available now unless it is explicitly enabled:

<! --
<roleService enabled="true" />
-- >

In the scriptResourceHandler section, you control whether requests for dynamic script are compressed or cached; normally, you want these features:

<! --
<scriptResourceHandler enableCompression="true" enableCaching="true" />
-- >

</scripting>
</system.web.extensions>

With script compression enabled, your server pays a small upfront price to do the compression, but text compresses well, and with caching enabled the amortized cost across multiple requests is almost nonexistent.

16.6.3. Configuring IIS7

IIS7 also introduces a new configuration section for your web.config file: system.webServer. IIS7 supports two modes: Classic and Integrated. Classic mode preserves backward compatibility in the way that ISAPI filters and extensions are called. In integrated mode, the old model is replaced by a new pipeline in which the two separate lifecycles of IIS and ASP.NET are merged into one for greater efficiency. The ScriptModule is added to the integrated mode pipeline. The httpHandler modifications made in the system.web section are duplicated in the handlers section of the new section.

This change isn't specific to ASP.NET AJAX, but you should be aware of the validation element, as it can cause confusion. The validateIntegratedModeConfiguration option is set to false. Setting this value to false means that it is not an error to have duplicate entries in the handler and httpHandlers sections and the modules and httpModules sections:

<system.webServer>
 <validation validateIntegratedModeConfiguration="false"/>
 <modules>
  <add name="ScriptModule" preCondition="integratedMode"
type="System.Web.Handlers.ScriptModule, System.Web.Extensions, Version=3.5.0.0,
Culture=neutral, PublicKeyToken=31bf3856ad364e35"/>
  </modules>
  <handlers>
   <remove name="WebServiceHandlerFactory-Integrated" />
   <add name="ScriptHandlerFactory" verb="*" path="*.asmx"
preCondition="integratedMode"
      type="System.Web.Script.Services.ScriptHandlerFactory,
System.Web.Extensions, Version=3.5.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35"/>
   <add name="ScriptHandlerFactoryAppServices" verb="*"
 path="*_AppService.axd" preCondition="integratedMode"
      type="System.Web.Script.Services.ScriptHandlerFactory,
System.Web.Extensions, Version=3.5.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35"/>
   <add name="ScriptResource" preCondition="integratedMode" verb="GET,HEAD"
path="ScriptResource.axd" type="System.Web.Handlers.ScriptResourceHandler,
System.Web.Extensions, Version=3.5.0.0, Culture=neutral,
PublicKeyToken=31bf3856ad364e35" />
  </handlers>
 </system.webServer>

The web.config template is larger than it used to be as a starting point but has everything necessary to get started and works across several versions of the Web server. One common symptom of a configuration error with the ScriptResource handler is an error message in the browser stating that objects in the Sys namespace are not defined. When running in debug mode, the error message is more explicit in its explanation that the AJAX Library did not load. This wouldn't typically be associated with deployment, but given the separate definitions for different versions of IIS, it is something to be aware of when moving from test to production environments.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset