Apache and Tomcat via Cpanel - Servlet Display Problems

November 7, 2007

Problem

Apache Web Server was not passing servlet requests to Apache Tomcat. Instead it served 404 errors, even though the Apache Tomcat Connector (JK 1.2, mod_jk) was auto-configured by the WHM / Cpanel installation.

Other Possible Descriptions of the Problem

  • Jsp’s work in Tomcat, but servlets do not
  • Apache Http Server won’t pass servlet requests to Tomcat
  • Tomcat problems using the Cpanel plugin
  • Virtual host configuration problem with Cpanel Tomcat
  • Apache not recognizing servlets
  • Servlets can’t be accessed through Apache

In the latest Cpanel Release (11.15.0-RELEASE 17853), Tomcat support has been integrated. Prior to this (I’m not sure for how long), Tomcat was available via a beta plug-in. I experienced this problem with both the beta plug-in and the integrated support.

What’s Happening

Apache Http Server accepts all web requests and determines which are requests for static content, and which requests should be forwarded to Tomcat.

Apache correctly serves static content, and correctly passes all requests for .jsp pages to Tomcat. But when a servlet is requested, e.g. www.myserver.com/myapp/myservlet, Apache looks for the “/myapp/myservlet” directory, and finding none, spits out a 404 error.

How to Resolve the Problem

I tried several things that I thought should work but did not, though I don’t know if it was due to my specific configuration or because they were just the wrong things to do. What finally solved the problem was just adding an .htaccess file to the root of the web application with the following lines:

SetHandler jakarta-servlet
SetEnv JK_WORKER_NAME ajp13

This forces Apache to forward all requests to resources within this context to Tomcat for processing, specifically to worker ajp13. Ajp13 is one of the default workers set up, and is defined (on my system) in /usr/local/jakarta/tomcat/conf/workers.properties.

Other things that I thought should work but didn’t (your mileage may vary):

1) In /etc/httpd/conf/jk.conf (if your httpd.conf file includes jk.conf),
add/edit the switch “+ForwardDirectories.” Normally, if Apache runs
across a directory it doesn’t recognize, it will spit out a 404. This
switch says to forward those requests to Tomcat, and let Tomcat spit
out a 404 if it can’t fulfill the request.

2) In /etc/httpd/conf/jk.conf (if your httpd.conf file includes jk.conf), specifically mount each context, and unmount static content. Mounting tells Apache to pass requests to Tomcat, and unmounting tells Apache to serve the content itself. Newer versions of Tomcat are faster than Apache at serving static content, but apparently, using Apache to serve static content is safer from a security perspective.

JkMount /mywebapp/* ajp13
JkUnMount /*.gif ajp13
JkUnMount /*.jpg ajp13

A separate issue that is outside the scope of this post is whether you should use Apache Web Server to front Tomcat requests, or whether you should just have Tomcat accept requests over port 80. If you’re using a recent Tomcat version (5.5+), Tomcat can serve both static and dynamic content faster than Apache.

Use Tomcat if: 1) you’re only dealing with a single server; 2) and you’re not using any other software that requires Apache (e.g. forums or wikis written in PHP).

Use Apache to front Tomcat requests if: 1) you want to load balance across multiple servers; 2) or you want different web applications or virtual hosts to be served by different processes.

Disclaimer

I know embarrassingly little about hardware, networking, or server setup. This solution might be a hack or it might be obvious to some more familiar with the components mentioned, but it couldn’t be resolved through a dedicated server help desk or through the Cpanel help desk, so I assume there are others out there that this could help. Everything in this post is based on my limited experience with the aforementioned software and my own research. If you know of a better, cleaner way to do this, or if you know how better to describe this problem or solution, please forward to me and I’ll amend this post.

Rationale Behind this Post

I recently (as in yesterday) resolved a difficult to diagnose problem involving Cpanel, Apache Web Server, Apache Tomcat, and the Apache Tomcat Connector (JK 1.2, mod_jk2). My googling skills tend to be above average, but I could find no reference to this specific problem anywhere, and the sole purpose of this post is to hopefully save someone else the aggravation. So please disregard the keyword-heavy text — it’s altruistic in nature, I assure you.