Prizes & Awards
My Profile
Active Members
TodayLast 7 Days
more...
|
Resources » Articles » ASP.NET/Web Applications »
Performance Tuning in ASp.Net
|
Some of the main issues that affect the Performance and Scalability of ASP.NET applications are listed below:
Failure to Share Expensive Resources
Database connection is an example for an expensive resource. Failing to close or dispose such resources in an application might lead to resource shortage. The resources can be utilized efficiently if measures are taken to close or dispose them.
Making Late Bound Calls
A late bound call requires extra instructions to identify and load the code to be executed. It is better to avoid such instructions.
Blocking Operations
A single thread handles ASP.NET page request. This thread gets blocked if it is waiting for a response in return to the request made which prevents it from servicing other user requests efficiently.
Misusing Threads
Threads are created for every request. The initialization costs become more if threads are created unnecessarily. On the other side, if single threaded apartment COM components are improperly used it might build up queues which in turn might reduce the performance. Improper Caching
While caching data caution should be taken not to cache dynamic and infrequently used data, cache the static data.
Large Pages
The size of the page is affected by the number and type of controls, data and the images used to render the page. A network bottleneck is created if huge data is sent on the wire, consuming more bandwidth.
Inefficient Rendering
The issues like switching between HTML and server code, performing initialization code for every post back and late binding can cause considerable rendering overhead. This can decrease the page performance.
Session State
If one is not using Session State turn it off by adding <@%EnabledSessionState = false %> to the asp page. There are several options available for EnableSessionState that can be set depending on the requirement.
View State
Use of view state eats up memory and performance. So turn it off by adding <@% EnabledViewState = false %> if not required. The performance in this case is hit because there is a round-trip signal which is sent across the network each time the page is loaded to update and verify the cache.
Encode using ASCII when UTF is not required
By default, ASP.NET comes configured to encode requests and responses as UTF-8. If the application needs only ASCII, then eliminate the UTF overhead which gives back a few cycles. Note that this can only be done on a per-application basis.
Authentication Procedure
Choose a cheapest way to authenticate the user depending on the requirement (in order of increasing cost: None, Windows, Forms, Passport).
Batch work
Avoid round trips to the server by batching requests together. This principal can be applied to data access code by batching SQL commands together using ";" and to remote object calls by proving granular interfaces that perform logical operations through a single method call. Considerations to tackle Performance and Scalability Issues
Design Considerations
Partition the Application Logically
Partition the application into presentation, business and data access layers. This helps in easy maintenance of code and allows monitoring and optimizing the performance of each layer separately. One can deploy each of these layers onto a single web server but physical separation of layers gives chance for deployment on multiple servers. One should remember that call latency increases if the layers are physically separated. For example, in process calls are faster, followed by cross process calls on the same computer, followed by remote calls. To achieve optimum performance place the business and data access layers in the \bin directory of the web server.
Avoid Blocking Operations
Free the Web server to process other incoming requests by using asynchronous mechanisms like · Use asynchronous calls to invoke Web services or remote objects. This allows the Web server to invoke code and if necessary be notified when the work is completed. · Use the OneWay attribute on Web methods or remote object methods if a response is not required. In this case the Web server makes a call and continues processing. · Queue work and polling for completion from the client. This allows the Web server to invoke the code and let the Web client poll the server to see when the work has completed.
Avoid Exceptions
Catching exceptions is expensive, hence design code to avoid exceptions. Do not use exceptions to control logic flow. Validate user input and check for known conditions that can cause exceptions. Catch and handle exceptions close to where they occur to avoid extensive stack traversal and manipulation which is expensive. Implement an exception logging mechanism that captures detailed information about exceptions so that administrators and developers can identify and remedy any issues but avoid displaying detailed exception information to user for security purposes and to reduce the amount of data sent to the client.
Caching
Caching is particularly useful when the web application constantly relies on data from remote resources such as databases, web services, remote application server etc. Applications that are database intensive can benefit from caching by reducing the load on the database and increasing the throughput of the application. For caching to be effective the data or output should be static or infrequently modified. Choose appropriate caching method to cache data depending on the application requirement. Application-wide data is typically stored in the Application object or the Data Cache. User-specific data is typically stored in Session state or some other means. Static pages can be cached using the ASP.NET Output Cache. Static content within pages can be cached using a combination of the Output Cache and User Controls.
Session State
There are three options to store session state in ASP.NET. Each option offers varying degree of performance as stated below:
· InProc: The in-process provider provides the fastest access to session state. There is no serialization or marshalling costs involved as state is maintained in the ASP.NET process. But if lots of session states are stored then it consumes large amounts of memory on the Web server which can negatively impact performance. This approach also limits the ability to scale the application because this cannot be deployed in a Web farm or in an application pool in Windows 2003. · StateServer: The session state service (a regular Win32 service) can be installed on the Web server or on a remote server accessible by all Web servers in a Web farm. This approach scales well, but performance is reduced in comparison to the in-process provider due to the additional serialization and marshalling that is required to transfer the state to and from the state store. · SQLServer: For large amounts of session state SQL Server database is the best fit. Serialization and marshalling costs are the same as the session state service although the overall performance is slightly reduced. Security
Filter unwanted traffic and stop invalid requests from reaching the Web Server to reduce the server load which in turn, will increase the performance. The application’s performance can be boosted by following the below listed recommendations,
· Validate User Input: Perform validation checks on client side before passing invalid input data to server side. But it is preferable to cross check the input on the server side also · Avoid Per Request Impersonation: It is better to have a trusted connection with a single service account for all users to access database instead of an account for each individual user because the latter prevents the effective use of database connection pooling. · Segregate Secure and Non-Secure Content: It is recommended to segregate the publicly accessible areas and restricted areas that require authenticated access and SSL under separate subfolders beneath the application's virtual root. By doing so, one can use HTTPS for specific pages without incurring the SSL performance overhead across the entire site. · Tune SSL Timeout to Avoid SSL Session Expiration: The largest performance hit when using SSL occurs during the initial handshake, where asymmetric public/private-key encryption is used. After a secure session key is generated and exchanged, faster, symmetric encryption is used to encrypt application data. Monitor the SSL connections and increase the value of the ServerCacheTime registry entry if one finds that a longer time is more appropriate.
Data Access Layer Considerations
Following are few tips for data access layer design,
Design Effectively for Large Databases
Very large database is a database above 100 GB. Consider the following issues for very large databases
- Partition the tables containing millions of rows that can be key range partitioned. An example where key range partition can be used is where the data is accessed by date. There can be 12 partitions for each of the month. If data has to be fetched for a particular month only partition belonging to that month will be made use of in the query eliminating the other partitions. In this case partition will be handy if query is being used to access data across all months else if it is used to retrieve latest month’s data then partition will not improve the performance as most of the queries will be going to be the same IO device.
- Increase RAM size and processor power to improve database performance. Use 64 bit edition of the database to produce better performance than its 32 bit equivalent.
- Build indexed views to minimize spending time in retrieving large data from the database when the data changes are not often.
- Choose data types carefully. Use Varchar instead of char to save space, minimize IO and improve performance.
- Try to partition data according to the needs of the location. Eg: In case of consolidating reports there might be requirement for cross database joins. If data is partitioned improperly then it will result in maintenance and performance problems.
Use Connection Pooling
Use data provider's inbuilt connection pooling to avoid connection overhead and to allow limited connections to be effectively shared by multiple users. Use the trusted subsystem model to access downstream systems and databases to ensure effective use of connect pooling.
Minimize Round Trips
Minimize the number of round trips between the application and the database. This can be achieved by following few options like, avoid excessive use of triggers, avoid updating the database with unchanged data, avoid manipulation of string parameters in stored procedures (e.g. Avoid using dynamic SQL within stored procedures).
Design for Data Locking
There are two main options for data locking, Pessimistic and Optimistic Locking. Though Pessimistic locking brings down the performance, certain business scenarios do not accept simultaneous update of data. In such scenarios one should use Pessimistic locking. On the other hand Optimistic locking provides high response time and can be implemented by making use of the user name and update date time stamp in all tables.
Development Considerations
A few performance tips for VB.Net development Explicitly Declare Variable Types in VB.NET and JScript
Use the explicit type declaration,
Dim x as String Dim y as Integer
Do not use the following, Dim x as Object Dim Y
Use Binary compare for Text
When comparing text, use binary compare instead of text compare. At run time, the overhead is much lighter for binary.
Use Charw
Use Charw instead of Char. The CLR uses Unicode internally, and char must be translated at run time if it is used. This can result in a substantial performance loss, and specifying that the characters are a full word long (using charw) eliminates this conversion.
Use Early Binding
If the variable data type is know in advance, then it is better to use early binding because this avoids strange errors and enhances performance. Also, turn Option Explicit option on which forces one to declare the variable before it is used thus checking type errors during compilation rather that at run-time.
Optimize Assignment
Avoid X = X+1 Use X += 1
In the first statement, JIT evaluates “X” twice unnecessarily. This can be overcome using the second statement.
Concatenate statements in a single Expression
If multiple concatenations on multiple lines are to be handled, try to concatenate them in a single expression using StringBuilder. If a string is modified repeatedly, the compiler will create a new string always leaving the original to be garbage collected which burdens the performance. Avoid
Dim Count as integer Dim Str as string
For Count = 0 to 100 Str = Str + “Hello” Next Count
Use
Dim Count as integer Dim Str as StringBuilder For Count = 0 to 100 Str.Append(“Hello”) Next Count
Include Return Statements
For every function in Visual Basic, explicitly use a return statement to return the value. No doubt that the function will return a value without the return statement but if the function has several local variables on the stack without return keyword, it becomes harder for the JIT to optimize and provide the results faster. By using return keyword, the application can be speeded up.
Reduce Roundtrips
Use the following techniques and features in ASP.NET to minimize the number of roundtrips between Web server and browser and Web server and downstream system:
· Client.IsConnected: Use this to check if the client is still connected before processing a request and performing expensive server side operation. · Use Page.IsPostBack to minimize redundant processing if (Page.IsPostBack = false) then ‘Write Initialization logic else ‘Write Client post-back end if
· Output Caching: If the application is fetching, transforming and rendering static data then caching can be used and redundant hits can be avoided.
· Output Buffering: Buffer the output to reduce roundtrips. This works fine on the server and avoids chatty communication with the client. But the back log of this is, for a slow page, the client won't see any rendering of the page until it is complete. To overcome this one should use Response.Flush which sends output up to that point to the client.
· Server.Transfer: It is preferable to use Server.Transfer instead of Response.Redirect where ever possible. The Response.Redirect method sends a meta-tag to the client that causes the client to send a new request back to the server, using the new URL. Server.Transfer avoids this level of indirection by simply making a server-side call.
· Local Variables: Use local variables within a loop if the data has to be fetched instead of making outgoing calls to fetch the data for each iteration. Also reduce the creation and destruction of any resources that consumes memory outside the loop instead of performing it inside the loop.
· Data Caching: Cache variables instead of performing multiple lookups. For example, if one needs to look up server variables multiple times then cache them.
Data Binding
Consider the following while calling the databind
· Avoid Using Page.DataBind: When DataBind is called, the Databind method at the page level is invoked which internally calls Databind of all controls in that page which impacts performance. Instead call DataBind on specific control. I.e.
Avoid
DataBind()
Use
Control.DataBind()
· Use a DataReader for Fast and Efficient Data Binding: Use DataReader to load data into a control quickly if caching is not required. DataReader is the best choice for retrieving read only data in a forward only manner. Loading the data into dataset and then binding the dataset to a control moves data twice and incurs significant expense in constructing the dataset. If there is no need to cache data and if data has to be loaded into a control as quickly as possible use a DataReader. The DataReader is the optimum choice for retrieving read only data in a forward only manner. Loading the data into a Dataset and then binding the Dataset to the control moves the data twice and also incurs the relatively significant expense of constructing a Dataset. Execute a query and bind using a DataReader for optimum performance as shown below:
Dim cmd as new SqlCommand() Dim dr as SqlDataReader
cmd.CommandText = “Select CustomerID, CustomerName from Customers” dr = cmd.ExecuteReader() myctl.DataSource = dr myctl.DataTextField = “CustomerName” myctl.DataValueField = “CustomerID” myctl.DataBind()
Performance Testing
Performance testing is the process of determining and reporting the performance of an application. The different types of performance related testing are:
· Load Testing: In this type of testing, the application performance is tested based on how it can handle number of users in key use case scenarios. Expected load is simulated by creating and running tests and collecting data at different points to determine the performance. The load is incrementally increased till expected peak load is reached and performance is recorded.
· Stress Testing: In this type of testing, the “weak” points of the application are tested when huge demands are placed on it. It checks whether the system functions normally after a failure or if any reset of the application is required.
· Endurance Testing: If the system has to run continuously for a long period, then it has to be thoroughly tested for memory and resource leaks before it is being deployed.
There are several tools available to do performance testing. Microsoft provides Application Center Test to perform Stress Testing.
A brief on Application Center Test
The ACT is designed to stress test Web servers and analyze performance and scalability problems with Web applications, including Active Server Pages (ASP) and the components they use. It simulates a large group of users by opening multiple connections to the server and rapidly sending HTTP requests. It supports different authentication schemes and the SSL protocol, making it ideal for testing personalized and secure sites. The ACT user interface consists of a script editor, user manager, test projects and wizards to help create and perform tests.
Creating and Running Tests
In order to test an application’s performance as to how it performs when multiple users use it, ACT provides the following steps,
· Create an ACT Project: A project is a container for a single or multiple tests required to test an application.
A project has to created before creating a test
o Click Start, click All Programs, click Microsoft Visual Studio .NET 2003, click Visual Studio .NET Enterprise Features, click Microsoft Application Center Test. o On the File menu, click New Project. o In the New Project dialog box, enter TestProject for the Name, and then click OK.
Set Debugging Option for the Project (or changing log file location): The default ACT writes the log file to the ACT installation directory. The log file contains the contents of any Test.Trace method used in the test script.
To set debugging options for all tests in the project,
o On the Actions Menu, click Properties. o In the Properties dialog box, click Debugging. o In the Folder to save log to, browse to suitable folder and click OK.
· Create a Test: The test can be created manually or one can allow ACT to record user interactions with the application.
To create the test manually,
o Right click the Tests folder and select the Create an empty test option and click Next. o Select the scripting language from the list and click Next. o Type a name in the Test name box and click Next. o Click Finish.
To create the test by recording the browser activity, o Right click the Tests folder and select the Record new test option and click Next. o Select one of the test type options and click Next. o Click Start recording when ready to begin browsing with Internet Explorer. o Click Stop recording to stop recording. The recording can be stopped and restarted any number of times. Once the recording is done, click Next. o In the Test Options dialog box, type a name in the Test name box and click Next. o Click Finish.
· Set Test Properties: The details about the requests sent to the browser can be determined by setting the test’s properties
1. Set Load Level: ACT can open multiple connections to a Web server and can send request on each of the connection.
To set the load level of the test: o Right click test’s name and select Properties. o Select the General tab. o In the Simultaneous browser connections box, type a value. ACT will attempt to achieve this load level during the test run. Note that this value sets the number of copies of the test script that are running simultaneously. If more than one Connection object is created in the test, the actual number of HTTP connections to the server will be higher than the Simultaneous browser connections value.
2. Set Test Duration: The test can be run for a specified amount of time or for a given number of iterations.
To set the duration of the test:
o Right click test’s name and select Properties o Select the General tab o An optional warm up time can be set. During the start, the Web application or Server might be taking some time to initialize components or adjusting cache data. If warm up time is set by typing a number in the Warm-up time box in the Test Duration area, then the data produced during that time will not be included in the reports. o Duration of the test run can be set in two ways. To make the test run for a specific length of time, select the Run test for a set time option, and type the number of days, hours, minutes and seconds to use for the test run in the appropriate boxes. To make the test run for a specific number of iterations on each client, select the Run test a specific number of iterations option and specify a value.
Note: Administrator rights are required to view the performance counters on local and remote computers
3. Add and Configure Performance Counters:
To set the duration of the test: o Right click test’s name and select Properties. o Select the Counters tab. o The Counter Collection interval box allows one to specify how often the counter data is sampled. Note that increasing collection rate by decreasing time might reduce the performance of ACT client when many counters are used. o Click Add button to open the Browse Performance Counters window. Select the appropriate computer, performance object, counter, and counter instance. Click the Add button to add it to the test. Click the Explain button to see a detailed description of the selected counter if necessary. o Click the Close button when done. Click OK to close the Test Properties dialog box
4. Important Counters for Web Testing: Performance counter data is used to determine when a test client or Web server has reached its maximum CPU use. In cases where the performance bottleneck for the Web application is not the server CPU, performance counters will be the easiest way to determine where the bottleneck is occurring.
Some counters should be used in all tests (those shown in Bold type in the following lists), while others will only be helpful when trying to find less obvious sources of performance problems
|
Responses
|
| Author: Balamurali Balaji 26 Nov 2004 | Member Level: Diamond Points : 0 | Congradulations Rakesh Sharma,
Your article explored everything about asp.net performance tuning and is a real treasure to .net developers. It would definitely be helpful to everyone who wanted their web applications work nicely.
I'd urge everyone and the .Netspider team members to read this article.
congrats, once again!
| | Author: Rakesh Chander Sharma 05 Jan 2005 | Member Level: Silver Points : 0 | Thanx Murali, i would like to share such interesting topics with you guys in future also.
Rakesh Sharma
| | Author: Debasmit Samal 11 Jan 2005 | Member Level: Gold Points : 0 | Hi Rakesh Wahhh.... What a topic u have submitted.First time i got this perticular topic today. Really it is nice
Thanks
| | Author: Amrendra Kumar 10 Mar 2005 | Member Level: Bronze Points : 0 | I would like to know the difference b/e # of current logical Threads and \asp .net Request Executing.
In spite the setting the worker thread 250 at the load of 200 users iam seeing <80 Request Executing and some Request Queued. My \asp .net application (Request in Application Queue) is showing value 0 always.
|
|