Resource icon

Performance Tuning A Tomcat Server

  • perf-test.com need your contributions to build up a strong repository of performance engineering resources.

The following steps are used to improve the performance of the tomcat server,

  1. Increase JVM heap memory
  2. Resolve JRE memory leaks
  3. Connector setting
  4. Compression
  5. Database performance tuning
  6. Tomcat Native Library
  7. Other options
Tuning JVM:

If your JVM supports both green and native threads, you should try both models to determine the best choice for your site. Native threads offer the best performance, especially if you are running a lot of I/O bound applications (which is very likely, since you are running Tomcat). However, green threads outperform native threads in some specific areas, such as synchronization and thread activation. Green threads will decrease the load placed on your machine. Try both and see which option gives you the biggest performance boost.


Step 1 – Increase JVM heap memory

OutOfMemoryError”: The reason for this error is tomcat has very small memory for the running process, this error can be resolved by doing some changes in the Tomcat configuration file named “catalina.bat(In windows)/catalina.sh(In Linux)”. The change to be made is to increase the JVM heap memory. That is, the JVM does not invoke the garbage collector often, so the server can focus more in serving web requests and the requests are completed faster. The file(catalina.sh) to be changed is located at “\tomcat server folder\bin\catalina.sh” and the configuration to be made in this file is given below,


JAVA_OPTS="-Djava.awt.headless=true -Dfile.encoding=UTF-8


-server -Xms1024m -Xmx1024m



-XX:NewSize=512m -XX:MaxNewSize=512m -XX:permSize=512m


-XX:MaxPermSize=512m -XX:+DisableExplicitGC"

-Xms – Specifies the initial heap memory
-Xmx – Specifies the maximum heap memory
The changes will gets activated, Once you restart the Tomcat Server.


Step 2 – Resolve JRE memory leaks
Another main reason for the performance lack is memory leak. Always use the latest tomcat server to get better performance and scalability. This error can be resolved if we use the latest tomcat server version 6.0.26 and above since it contains a listener to handle the JRE and permgen memory leak. The listener used here is,

<Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener"/>

You can find the above listener class configuration in the server.xml file which resides in “tomcat project folder/conf/server.xml”.


Step 3 – Connector setting : This step shows how to tune the connector attributes:

i) maxThreads

ii) enableLooksups

iii) connectionTimeout

iv) maxConnections

v) tcpNoDelay


i) maxThreads:

Thread pool specifies the number of web request load that comes in, So this part should be handled carefully in order to get the better performance. This can be accomplished by tuning the connector attribute “maxThreads”. The value of the maxThreads should be based on the volume of the traffic. If the value is low, then there will not be enough threads to handle all of the requests, so it undergoes in to the wait state and comes back only when an another request thread gets freed. If we set maxThreads value too high means then the Tomcat startup time will take longer. So its up to us, Put a right value in the maxThreads.


<Connector port="8080"address="localhost"


maxThreads="250"maxHttpHeaderSize="8192"



emptySessionPath="true"protocol="HTTP/1.1"


enableLookups="false"redirectPort="8181"acceptCount="100"


connectionTimeout="20000"disableUploadTimeout="true"/>

In the preceding configuration, maxThreads value is given as “250″. This specifies the maximum number of simultaneousrequests that can be handled by the server. If not specified, the default value of this attribute “200″. Any further simultaneous requests will receive “connection refused” errors until the another request gets freed. The error looks like the below,


org.apache.tomcat.util.threads.ThreadPool logFull SEVERE: All threads (250) are currently busy, waiting. Increase maxThreads (250) or check the servlet status

If the application results in the above error, Always investigate whether the above error caused by a single request that takes too long. The reason is, Sometimes if the database connection is not released means, it will not allow to process additional request.

Note: If the number of request exceeds “750″ means, Instead of setting the value “750″ in the maxThreads attribute, Its better to go for the “Tomcat Clustering” with multiple tomcat instances. That is, In the case of “1000″ request, set “maxThreads=500″ for the two instances of tomcat, Instead of a single Tomcat with maxThreads=1000.

ii) enableLooksups:

In Java Servlet Code, user can look up request message origin (IP or URL).

For example user in yahoo.com send request to server, and Tomcat try to resolve incoming request IP address. “enableLooksups” option enables return DNS name not a IP address. During this processing Tomcat look up DNS. It brings performance degradation. This option removes DNS look up stage and increase performance.


enableLookups=”false”


iii) connectionTimeout: connectionTimeout=”10000″


It is HTTP Connection time out (client to server). It is milliseconds. (10,000 = 10 sec).

If server cannot make a connection from client til 10 sec. It will throw HTTP time out error. In normal situation, our API response time is under 5 sec. So 10 sec means, server has been overloaded.



iv) maxConnections: maxConnections=”8192″

The maximum number of connection, tomcat can handle. It means tomcat can handle maximum 8192 socket connection in a time.

v) tcpNoDelay: tcpNoDelay=”true”

This allows us to use TCP_NO_DELAY in tcp/ip layer. It makes send small packet without delay. In TCP, to reduce small package congestion, it gathers small packet to tcp buffer until it has been filled and send the packet. TCP_NO_DELAY option makes send small packet immediately even though TCP buffer is not full.


Step 4 – Compression: This step shows how to compress the mime types.

Tomcat has an option to compress the mime-types by doing some configuration in the server.xml file. This compression should be done in the connector like the below,


<Connector port="8080"protocol="HTTP/1.1"


connectionTimeout="20000"



redirectPort="8181"compression="500"


compressableMimeType="text/html,text/xml,text/plain,application/octet-stream"/>

In the preceding configuration, the files will be compressed when the number of bytes is >= 500. If the files not to be compressed by the size means, Set the attribute compression=”on”. Otherwise the default the setting in Tomcat is “off”.

NOTE: If we are using REST protocol then we will consider switching compression ‘off’.


Step 5- Database performance tuning: This step shows how to tune the database.

Tomcats performance gets lacked while waiting for the database queries to get executed. Nowadays most of the application uses Relational databases, which may contains “NamedQueries”. If so, by default the tomcat will load the named queries initially, this may increase the performance. Another important thing is, always ensure that all the database connections are closed properly. Also setting the correct value in the database connection pool is very essential. I mean the values in maxIdle, maxActive, and maxWait attributes of the Resource element. Since the configuration depends on the application requirements. The correct values can be decided by invoking the performance testing for the database.


Step 6 – Tomcat Native Library

Tomcat native library, “Apache Portable Runtime(APR)” provides superior scalability, performance and better integration with the native server technologies and gives optimal performance in the production environment. The installation steps is explained below:

If the APR is not installed then the Tomcat startup catalina.log file will produce the following information:

org.apache.catalina.core.AprLifecycleListener init
INFO: The APR based Apache Tomcat Native library which allows optimal performance in production environments was not found on the java.library.path: /usr/lib/jvm/java-6-sun-1.6.0.22/jre/lib/i386/server:/usr/lib/jvm/java-6-sun-1.6.0.22/jre/lib/i386:/usr/lib/jvm/java-6-sun-1.6.0.22/jre/../lib/i386:/usr/lib:/usr/lib:/usr/lib/jvm/java-6-sun-1.6.0.22/jre/lib/i386/client:/usr/lib/jvm/java-6-sun-1.6.0.22/jre/lib/i386:/usr/lib/jvm/java-6-sun-1.6.0.22/jre/../lib/i386:/usr/java/packages/lib/i386:/lib:/usr/lib

Next step is to install the APR. Following are the steps to install the APR on Windows and Ubuntu:

i) Windows
Download the 1.1.19 tcnative-1.dll file from the tomcat official site.

Place the file in the tomcat bin directory. “c:/program files/tomcat 6.0.29/bin”

Restart the tomcat server.

Note: Place the correct version of the tcnative-1.dll file in the bin directory. If the lower version is placed, the catalina.log file will contains the informations as specified below:

org.apache.catalina.core.AprLifecycleListener init
SEVERE: An incompatible version 1.1.16 of the APR based Apache Tomcat Native library is installed, while Tomcat requires version 1.1.19

If the installation is successful, the outcome of the tomcat start up catalina log will contains the information as specified below:

org.apache.catalina.core.AprLifecycleListener init
INFO: Loaded APR based Apache Tomcat Native library 1.1.19.

ii) Ubuntu
Ubuntu has supported packages for both Tomcat 6 and 7. Tomcat 6 is the legacy version, and Tomcat 7 is the current version where new features are implemented. Both are considered stable.

In ubuntu, Open the terminal and execute the following command and then restart the tomcat server,


sudo apt-get install tomcat7

If the tomcat native libraries is installed successfully, the tomcat catalina start up log files contains the following informations,

org.apache.catalina.core.AprLifecycleListener init
INFO: Loaded APR based Apache Tomcat Native library 1.1.19.

Step 7 – Other options:
Some of the other options are,

  • Enable the web browser cache, so that the static content which resides in the webapps folder loads faster. By doing this the performance is greatly increased.
  • Tomcat server should be automatically restarted, whenever the machine starts.
  • Normally HTTPS request is slow when compared to the HTTP request. But whatever if you want some good security for the application means, we should prefer HTTPS instead of HTTP.
  • Use of Apache HTTPD to proxy your requests should be avoided at all costs, as it will decrease your performance by nearly 50%.
  • Consider factors such as the suitability of your protocol for the project. For example, if you are loading large amounts of data, and you need high performance, XML is the wrong choice.
Tools:

Use JProbe or OptimizeIt to search for any bottlenecks due to thread synchronization.

There are a number of tools available to help you keep an eye on JVM's performance. One of the most convenient solutions is VisualVM. Other commonly used JVM monitoring tools included with the SDK include console, jps, and jstack.
Author
anmoldubey
Views
72
First release
Last update
Rating
4.00 star(s) 1 ratings

More resources from anmoldubey

Latest reviews

Helpful to understand different tuning options..Thanks