Recent Posts

RSS Feeds

Low Cost Grails / Java Web Hosting - Clean Shutdown of Tomcat without another JVM

Stopping Tomcat the right way 

I like to do things the right and clean way. And shutting down a service under Linux is done by calling the start-/stop-script under /etc/init.d with the parameter stop. Even graphical front-ends, may they be YAST or webmin or whatever stick to this rule. The advantage is, the whole know-how of how to shutdown one specific service is hidden in the start-/stop-script. Killing a process directly is real evil, because the process (and dependend processes) don't get the chance to do whatever they have to before shutting down. Otherwise databases get corrupted, stale files claim disk space, memory is hogged by zombie processes and the like.

To shutdown Tomcat v5.5 under Debian 4 one would call for example

# /etc/init.d/tomcat5.5 stop

The Problem

But wait! Why does it take a 30 seconds of dots printed out followed by the message '(Killling)'? I wanted to shutdown and not kill Tomcat, it should go faster and there is a port 8005 waiting for the message 'SHUTDOWN'. Apparently someting goes wrong. Further investigation revealed that low memory is the problem, again.

 The real shutdown is delegated to the script

/usr/share/tomcat5.5/bin/catalina.sh

which tries to delegate it further to some Java program. But there is already one running - Tomcat - and it takes almost all memory there is left. So even the smallest JVM start will fail, for example

# java -version -Xms32m -Xmx32m

So every call of tomcat5.5. stop fails, and the Debian script is smart enough to kill the Tomcat process after 30 seconds (adjustable in the script by variable TOMCAT5_SHUTDOWN=30)

Solution

The solution is simple: Tell Tomcat to shutdown itself without any additional Java process. We have to send the message 'shutdown' to localhost at port 8005. For these purpose there is a small but mighty tool an Linux systems: Netcat - the swiss army knife of the network.

So replace in /usr/share/tomcat5.5/bin/catalina.sh the code to stop via Java by a call to Netcat (nc):

#  "$_RUNJAVA" $JAVA_OPTS $CATALINA_OPTS \
#    -Djava.endorsed.dirs="$JAVA_ENDORSED_DIRS" -classpath "$CLASSPATH" \
#    -Dcatalina.base="$CATALINA_BASE" \
#    -Dcatalina.home="$CATALINA_HOME" \
#    -Djava.io.tmpdir="$CATALINA_TMPDIR" \
#    org.apache.catalina.startup.Bootstrap "$@" stop

echo SHUTDOWN | /bin/nc localhost 8005

If you try to call

/etc/init.d/tomcat5.5 stop

again it'll take only 2.3 seconds (dots) and all is clean and shutdown. And as a bonus this will also happen every time you ( or your provider) shuts down your Linux box as well.


  Share

Permalink     Kommentare[1]

Related Articles:

Kommentare:

I have been trying to figure out a way to restart tomcat in windows but have been having some issues. I am have a web app which is running a series of projects on the computer. At the end of the run I want to call a batch file while will restart tomcat (to free up resources). This batch file just has a stop and start tomcat commands. The problem is after the stop command, the web app shuts down (cause tomcat is down) so the start tomcat never gets executed. Is that anyway to restart tomcat via a batch or some other process.

Gesendet von Ali am May 09, 2008 at 10:07 PM CEST #

Senden Sie einen Kommentar:
Kommentare sind ausgeschaltet.