Preserve Session IDs of Tomcat cluster behind Apache reverse proxy / Sticky sessions with mod_proxy and Tomcat

apache_and_tomcat_merged_logo_prevent_sticky_sessions
Having a combination of Apache webservice Reverse Proxy to redirect invisibly traffic to a number of Tomcat server positioned in a DMZ is a classic task in big companies Corporate world.
Hence if you work for company like IBM or HP sooner or later you will need to configure Apache Webserver cluster with few running Jakarta Tomcat Application servers behind. Scenario with necessity to access a java based application via Tomcat which requires logging (authentication) relaying on establishing and keeping a session ID is probably one of the most common ones and if you do it for first time you will probably end up with Session ID issues.  Session ID issues are hard to capture at first as on first glimpse application will seem to be working but users will have to re-login all the time even though the programmers might have coded for a session to expiry in 30 minutes or so.

… I mean not having configured Session ID prevention to Tomcats will cause random authentication session expiries and users using the Tomcat app will be unable to normally access below application with authenticated credentials. The solution to these is known under term "Sticky sessions"
To configure Sticky sessions you need to already have configured Apache/s with following minimum configuration:

  • enabled mod_proxy, proxy_balancer_module, proxy_http_module and or mod_proxy_ajp (in Apache config)

  LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_balancer_module modules/mod_proxy_balancer.so
LoadModule proxy_http_module modules/mod_proxy_http.so

  • And configured and tested Tomcats running an Application reachable via AJP protocol

Below example assumes there is Reverse Proxy Load Balancer Apache which has to forward all traffic to 2 tomcats. The config can easily be extended for as many as necessary by adding more BalancerMembers.

In Apache webserver (apache2.conf / httpd.conf) you need to have JSESSIONID configured. These JSESSIONID is going to be appended to each client request from Reverse Proxy to each of Tomcat servers with value opened once on authentication to first Tomcat node to each of the other ones.

<Proxy balancer://mycluster>
BalancerMember ajp://10.16.166.53:11010/ route=delivery1
BalancerMember ajp://10.16.166.66:11010/ route=delivery2
</Proxy>

ProxyRequests Off
ProxyPass / balancer://mycluster/ stickysession=JSESSIONID
ProxyPassReverse / balancer://mycluster/

The two variables route=delivery1 and route=delivery2 are routed to hosts identificators that also has to be present in Tomcat server configurations
In Tomcat App server First Node (server.xml)

<Engine name="Catalina" defaultHost="localhost" jvmRoute="delivery1">

In Tomcat App server Second Node (server.xml)

<Engine name="Catalina" defaultHost="localhost" jvmRoute="delivery2">

Once Sticky Sessions are configured it is useful to be able to track they work fine this is possible through logging each of established JESSSIONIDs, to do so add in httpd.conf

LogFormat "%h %l %u %t "%r" %>s %b "%{Referer}i" "%{User-Agent}i""%{JSESSIONID}C"" combined

After modifications restart Apache and Tomcat to load new configs. In Apache access.log the proof should be the proof that sessions are preserved via JSESSIONID, there should be logs like:
 

127.0.0.1 - - [18/Sep/2013:10:02:02 +0800] "POST /examples/servlets/servlet/RequestParamExample HTTP/1.1" 200 662 "http://localhost/examples/servlets/servlet/RequestParamExample" "Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130807 Firefox/17.0""B80557A1D9B48EC1D73CF8C7482B7D46.server2"

127.0.0.1 - - [18/Sep/2013:10:02:06 +0800] "GET /examples/servlets/servlet/RequestInfoExample HTTP/1.1" 200 693 "http://localhost/examples/servlets/" "Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/20130807 Firefox/17.0""B80557A1D9B48EC1D73CF8C7482B7D46.server2"

That should solve problems with mysterious session expiries 🙂

Share this on:

More helpful Articles

Download PDFDownload PDF

Tags: , , , , , , , , , , , , , , , , , , , , , , , , , , , , , ,

3 Responses to “Preserve Session IDs of Tomcat cluster behind Apache reverse proxy / Sticky sessions with mod_proxy and Tomcat”

  1. hip0 says:
    Firefox 29.0 Firefox 29.0 Windows 7 x64 Edition Windows 7 x64 Edition
    Mozilla/5.0 (Windows NT 6.1; WOW64; rv:29.0) Gecko/20100101 Firefox/29.0

    Here are some other useful options; loadfactor, timeout and retry
    <Proxy balancer://mycluster>
    BalancerMember ajp://10.16.166.53:11010/ route=delivery1
    BalancerMember ajp://10.16.166.66:11010/ route=delivery2
    </Proxy>

    <Proxy balancer://mycluster>
    BalancerMember ajp://10.16.166.53:11010/ route=delivery1 loadfactor=20
    BalancerMember ajp://10.16.166.66:11010/ route=delivery2 loadfactor=5
    </Proxy>

    What is loadfactor? – This is the member load factor – a number between 1 (default) and 100, which defines the weighted load to be applied to the member in question.

    Also very important to know is timeout – sets timeout after which if Apache is unable to reach balancermember will timeout and
    retry – instructing Apache to try to reconnect again in (number of seconds), retry=1 will try to reach again defined balancemember in 1 seconds time, retry=0 and retry=1 are often useful when there are timeout issues. If retry is not set default retry interval value is too high 10 seconds! reducing retry to 1 or 0 seconds will decrease wait times.

       <Proxy balancer://mycluster>
       BalancerMember ajp://10.16.166.48:11010/ route=delivery1 timeout=30 retry=1
       BalancerMember ajp://10.16.166.70:11010/ route=delivery2 timeout=30 retry=1
       </Proxy>

     

    View CommentView Comment
  2. admin says:
    Firefox 29.0 Firefox 29.0 Windows 7 x64 Edition Windows 7 x64 Edition
    Mozilla/5.0 (Windows NT 6.1; WOW64; rv:29.0) Gecko/20100101 Firefox/29.0

    One other note for those new to Tomcat is short explanation on maxThreads and acceptCount.setting in server.xml
     

    maxThreads – defines how many parallel connections Tomcat could serve (to Java VM).

    acceptCount – is the amount of message queue size, requests to Tomcat which are higher than the requests defined by maxThreads will be stored in a queue (those onhold queue could hold a maximum number of requets).

    View CommentView Comment
  3. admin says:
    Firefox 29.0 Firefox 29.0 Windows 7 x64 Edition Windows 7 x64 Edition
    Mozilla/5.0 (Windows NT 6.1; WOW64; rv:29.0) Gecko/20100101 Firefox/29.0

    If you get some timeouts issues from Tomcat to Apache Reverse Proxy. Try setting to BalancerMember max=64. This timeout issues are common for Apache to work with mod_worker, you should have a configuration like:

    <Proxy balancer://mycluster>
       BalancerMember ajp://10.16.166.48:11010/ route=delivery1 timeout=30 retry=1 max=64
       BalancerMember ajp://10.16.166.70:11010/ route=delivery2 timeout=30 retry=1 max=64
       </Proxy>

    View CommentView Comment

Leave a Reply

CommentLuv badge