Output redirection in Tomcat
A few times, working on my projects, I had wanted to get the application (running on my Tomcat server) output (System.out.println()) in a log file. Redirecting the output of tomcat directly from startup.bat did not yield any good result (for obvious reasons explained later), so I tried running the server directly from its class. To run tomcat server from its class just open up a cmd window and navigate to your Tomcat’s bin directory. Type in (or better copy-paste; that’s the best we software engineer can do) the following command:
java -Djava.util.logging.manager=org.apache.juli.ClassLoaderLogManager -Djava.util.logging.config.file="<tomcat-install-dir>\conf\logging.properties" -Djava.endorsed.dirs="<tomcat-install-dir>\common\endorsed" -classpath "<java-install-dir>\lib\tools.jar;<tomcat-install-dir>\bin\bootstrap.jar" -Dcatalina.base="<tomcat-install-dir>" -Dcatalina.home="<tomcat-install-dir>" -Djava.io.tmpdir="<tomcat-install-dir>\temp" org.apache.catalina.startup.Bootstrap start
You need to replace <tomcat-install-dir> above with the location where your Tomcat server has been installed and <java-install-dir> with the location where J2SDK has been installed.
Using the above command will start Tomcat for you, now the only thing left is the output redirection. So, you can simply add an output redirection to the above statement and you’ll be done; something like:
java -Djava.util. . . start > tomcat.log
The file tomcat.log will be created in the bin directory.
Here are a few more details that you might be interested in knowing. Using the output redirection sign as shown above, redirects the standard output stream by default. Meaning, whatever your application prints to the standard output stream would be directed to the given file. This standard output is represented by the number 1. So this implies that if you write the above command as:
java -Djava.util. . . start 1> tomcat.log
it would still mean the same thing.
Note that there is no space between 1 and >. If you give a space there, then 1 will be treated as one of the command line inputs to your program.
The various streams available are:
0 -> Standard Input (Keyboard)
1 -> Standard Output (Display/Screen)
2 -> Standard Error Output (Display/Screen)
You might know that Linux and NT systems treat everything as a file. So, considering the various streams as files, the values 1, 2 and 3 are referred to as Descriptors (identifiers which describe a file). You can print any of these files to any other file. So you can redirect your program’s standard output to the printer too :-)
Using this technique, you can filter out what you wish to see onscreen. Or, if you wish to send an error log to your client, you can redirect the standard error stream.
NOTE: If your application prints the error using System.out.println(), then you would never be able to capture the error stream. You must use System.err.println() to print any error information. Exception stack traces are printed to the error stream by default.
Coming back to the Tomcat issue, I found out that you can modify catalina.bat to capture the streams. Just go through this file and make sure that the variable _EXECJAVA, being used in that bat file, is assigned the value “java.exe” (or “<java-install-dir>\bin\java.exe”) in place of “start java” (or start “<java-install-dir”>\bin\java”).
start is a batch command which “Starts a separate window to run a specified program or command”. So, if your application starts in a separate window, your output redirection, which is for the current window, will be of no use.