User Tools

Site Tools


java:installationunderlinux

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revisionBoth sides next revision
java:installationunderlinux [2012/08/11 16:10] rlunarojava:installationunderlinux [2014/12/24 10:42] – external edit 127.0.0.1
Line 1: Line 1:
  
 +====== Installation of Tomcat under Linux ======
 +
 +===== Preface =====
 +
 +These notes are about installing Tomcat in a production environment under apache. This notes were taken while I were installing such product in a machine on a DMZ, so **security were my first concern in every step I took**. 
 +
 +Said that, it is possible that the document has misunderstandings and errors. Nobody is perfect. **Use it at your own risk**.
 +
 +The machine I am using is a Virtual Server with 32 bits and a SuSE 11.1 installed.
 +
 +===== Things we need to install =====
 +
 +You should have the JRE installed in your machine. You can download it from Oracle website. 
 +
 +Make sure that you have defined a environmen variable JRE_HOME that points to the location of the JRE. In other words, this command should work: 
 +
 +<code bash>
 +rluna@machine:~> ($JRE_HOME/bin/java -version)
 +java version "1.6.0_22"
 +Java(TM) SE Runtime Environment (build 1.6.0_22-b04)
 +Java HotSpot(TM) Client VM (build 17.1-b03, mixed mode)
 +</code>
 +
 +Yes, the version of java is a bit outdated. I've used the version that the current version of linux provided through the package manager. 
 +
 +===== Create a tomcat user and a tomcat group =====
 +
 +The idea is to create a "tomcat" user and a "tomcat" group, own all the files of tomcat with this user and run the service with this user: this prevent that, in case of god-knows-what, an attacker would gain root privileges easily.
 +
 +<code shell>
 +groupadd -r tomcat
 +useradd -m -r -g tomcat tomcat
 +</code>
 +
 +The ''-r'' option is to specify that the user must be a system account. 
 +
 +The ''-g'' is to specify that the default group for this account must be ''tomcat'' instead ''users'', as used to be. And finnaly the ''-m'' option is for creating a home directory. I prefer to create a home directory for this type of users, just for store there certain downloads or configuration files. 
 +
 +==== If you want to log in as the tomcat user ====
 +
 +As you may know, if you want to login as the user ''tomcat'' all you have to do is to change the shell: 
 +
 +<code>
 +useradd -s /bin/bash tomcat
 +</code>
 +
 +and, to return the user to the prior state, you only have to do the following: 
 +
 +<code>
 +useradd -s /bin/false tomcat
 +</code>
 +
 +==== Ensure that the user has an umask of 0027 or less ====
 +
 +This can be checked out entering as the tomcat user or checking the /etc directory. This is for not leaving open files to every other user in the system.
 +
 +===== Creating the directory =====
 +
 +I've choose /usr/local/share as the main directory. I've created a directory called ''apache-tomcat-7.0.22'' -this is the version I am using- and a link to this named ''tomcat'': the rest of the commands, or services will be refered to the ''/usr/local/share/tomcat'' dir. With this resource, it will be easy to upgrade tomcat simply by changing the link. 
 +
 +<code shell>
 +mkdir apache-tomcat-7.0.22
 +chown tomcat:tomcat apache-tomcat-7.0.22
 +chmod 750 apache-tomcat-7.0.22
 +ln -s apache-tomcat-7.0.22 tomcat
 +</code>
 +
 +
 +===== Copy the contents (beware with the permissions) =====
 +
 +Copy all the contents into the new location (or uncompress them), and make sure that the permissions are assigned to tomcat:tomcat and are the proper. 
 +
 +<code bash>
 +cp /home/tomcat/tmp/apache-tomcat-7.0.22/* . -R
 +chown tomcat:tomcat * -R
 +</code>
 +
 +
 +==== Do a basic cleanup ====
 +
 +I've seen that the Windows .bat files are in the /bin files. I suggest delete them. 
 +
 +
 +==== Checkpoint ====
 +
 +At this point, tomcat should start with the default configuration. It is a good idea to make a little test prior to further testing. 
 +
 +Log in as the tomcat user and run the server: 
 +
 +<code bash>
 +tomcat@machine:/usr/local/share/apache-tomcat-7.0.22/bin> ./startup.sh 
 +Using CATALINA_BASE:   /usr/local/share/apache-tomcat-7.0.22
 +Using CATALINA_HOME:   /usr/local/share/apache-tomcat-7.0.22
 +Using CATALINA_TMPDIR: /usr/local/share/apache-tomcat-7.0.22/temp
 +Using JRE_HOME:        /usr
 +Using CLASSPATH:       /usr/local/share/apache-tomcat-7.0.22/bin/bootstrap.jar:/usr/local/share/apache-tomcat-7.0.22/bin/tomcat-juli.jar
 +
 +</code>
 +
 +Open a web browser and point it to the http://localhost:8080 port. It should show a welcome message of tomcat. If not, check out what is wrong. A simple ''lynx http://localhost:8080'' should return something understandable.
 +
 +
 +==== Fine-tunning configuration ====
 +
 +
 +=== Location of log files ===
 +
 +SuSE has all their log files under /var/log, so I prefer respect this practice and move the logs of apache to this location. Now they are under /usr/local/share/tomcat/logs. 
 +
 +**First,** create a proper directory under /var/log, let's say /var/log/tomcat:
 +
 +<code bash>
 +# mkdir /var/log/tomcat
 +# chown tomcat:tomcat /var/log/tomcat
 +</code>
 +
 +Then, open the file CATALINA_HOME/conf/logging.properties --CATALINA_HOME is the directory Tomcat is installed, and is refered as this in the documentation-- and modify the following entries:
 +
 +
 +<code properties>
 +1catalina.org.apache.juli.FileHandler.level = FINE
 +1catalina.org.apache.juli.FileHandler.directory = ${catalina.base}/logs
 +1catalina.org.apache.juli.FileHandler.prefix = catalina.
 +
 +2localhost.org.apache.juli.FileHandler.level = FINE
 +2localhost.org.apache.juli.FileHandler.directory = ${catalina.base}/logs
 +2localhost.org.apache.juli.FileHandler.prefix = localhost.
 +
 +</code>
 +
 +When it appears ${catalina.base}/logs it should appear the new directory, /var/log/tomcat. 
 +
 +Open the "server.xml" file and change locate the "logs" old directory and replace by the new one, /var/log/tomcat. I've replace the following entries: 
 +
 +<code xml>
 +  <Valve className="org.apache.catalina.valves.AccessLogValve" 
 +         directory="logs"
 +         prefix="localhost_access_log." suffix=".txt" 
 +
 +</code>
 +
 +Go to the ''bin'' directory and open the file ''catalina.sh''. There is a configuration for the console of the server there. Locate this entry: 
 +
 +<code bash>
 +if [ -z "$CATALINA_OUT" ] ; then
 +  CATALINA_OUT="$CATALINA_BASE"/logs/catalina.out
 +fi
 +
 +</code>
 +
 +
 +And change for: 
 +
 +<code bash>
 +if [ -z "$CATALINA_OUT" ] ; then
 +  CATALINA_OUT=/var/log/tomcat/catalina.out      
 +fi
 +
 +</code>
 +
 +Delete the content of the "logs" directory and start again the server. If after running the server still appear content, you should check the configuration or the configuration. 
 +
 +If the checking were successful, remove the ''logs'' directory and create a symbolic link with the same name: just in case other user logged in the system and searched for the directory where it is supposed to be in a normal installation. 
 +
 +=== Location of config files ===
 +
 +Another step is to change the location of the config files and put them under ''/etc/tomcat'': it is the usual point where a normal user should look for. 
 +
 +== Creation of the directory under /etc ==
 +
 +<code bash>
 +machine:/etc # mkdir tomcat
 +machine:/etc # chown tomcat:tomcat tomcat 
 +</code>
 +
 +== Move the contents to the new location ==
 +
 +Log in as the tomcat user: 
 +
 +<code bash>
 +tomcat@machine:/usr/local/share/tomcat/conf> cp * /etc/tomcat/ -R
 +tomcat@machine:/usr/local/share/tomcat> tar -czf conf_orig.tgz conf/
 +tomcat@machine:/usr/local/share/tomcat> rm -r conf
 +tomcat@machine:/usr/local/share/tomcat> ln -s /etc/tomcat/ conf 
 +</code>
 +
 +===== Create a Service so that it will start automatically =====
 +
 +In general, it is a good idea to create a service that will start automatically when the server starts. And that will be gently stopped when the servers is shut down. 
 +
 +**How to do this??**
 +
 +One idea is to search in internet. But bear in mind that most modern Linux distributions comes with __examples__ of services ready to customize for your needs. These __examples__ are common called as ''skeletons'' and normally live --or rest, because they are skeletons, aren't they??-- in /etc. 
 +
 +Mess around the /etc directory of your installation or check /etc/rc.d/ or /etc/init.d in order to locate those scripts. 
 +
 +**Here I put the script I created for SuSE**
 +
 +<code bash>
 +#!/bin/sh
 +#
 +#     Script for start/stop tomcat. Based on template "skeleton"
 +#
 +#
 +#     This library is free software; you can redistribute it and/or modify it
 +#     under the terms of the GNU Lesser General Public License as published by
 +#     the Free Software Foundation; either version 2.1 of the License, or (at
 +#     your option) any later version.
 +#       
 +#     This library is distributed in the hope that it will be useful, but
 +#     WITHOUT ANY WARRANTY; without even the implied warranty of
 +#     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 +#     Lesser General Public License for more details.
 +#      
 +#     You should have received a copy of the GNU Lesser General Public
 +#     License along with this library; if not, write to the Free Software
 +#     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307,
 +#     USA.
 +#
 +# /etc/init.d/FOO
 +#   and its symbolic link
 +# /(usr/)sbin/rcFOO
 +#
 +#
 +# LSB compatible service control script; see http://www.linuxbase.org/spec/
 +
 +#
 +### BEGIN INIT INFO
 +# Provides:          tomcat
 +# Required-Start:    $syslog $remote_fs apache
 +# Should-Start:      $time ypbind smtp
 +# Required-Stop:     $syslog $remote_fs
 +# Should-Stop:       
 +# Default-Start:     3 5
 +# Default-Stop:      0 1 2 6
 +# Short-Description: Tomcat
 +# Description:       Start the Tomcat Application Server
 +### END INIT INFO
 +
 +# Any extensions to the keywords given above should be preceeded by 
 +# X-VendorTag- (X-UnitedLinux- X-SuSE- for us) according to LSB.
 +
 +# Notes on Required-Start/Should-Start:
 +# * There are two different issues that are solved by Required-Start
 +#    and Should-Start
 +# (a) Hard dependencies: This is used by the runlevel editor to determine
 +#     which services absolutely need to be started to make the start of
 +#     this service make sense. Example: nfsserver should have
 +#     Required-Start: $portmap
 +#     Also, required services are started before the dependent ones.
 +#     The runlevel editor will warn about such missing hard dependencies
 +#     and suggest enabling. During system startup, you may expect an error,
 +#     if the dependency is not fulfilled.
 +# (b) Specifying the init script ordering, not real (hard) dependencies.
 +#     This is needed by insserv to determine which service should be
 +#     started first (and at a later stage what services can be started
 +#     in parallel). The tag Should-Start: is used for this.
 +#     It tells, that if a service is available, it should be started
 +#     before. If not, never mind.
 +# * When specifying hard dependencies or ordering requirements, you can 
 +#   use names of services (contents of their Provides: section)
 +#   or pseudo names starting with a $. The following ones are available
 +#   according to LSB (1.1):
 +# $local_fs all local file systems are mounted
 +# (most services should need this!)
 +# $remote_fs all remote file systems are mounted
 +# (note that /usr may be remote, so
 +# many services should Require this!)
 +# $syslog system logging facility up
 +# $network low level networking (eth card, ...)
 +# $named hostname resolution available
 +# $netdaemons all network daemons are running
 +#   The $netdaemons pseudo service has been removed in LSB 1.2.
 +#   For now, we still offer it for backward compatibility.
 +#   These are new (LSB 1.2):
 +# $time the system time has been set correctly
 +# $portmap SunRPC portmapping service available
 +#   UnitedLinux extensions:
 +# $ALL indicates that a script should be inserted
 +# at the end
 +# * The services specified in the stop tags 
 +#   (Required-Stop/Should-Stop)
 +#   specify which services need to be still running when this service
 +#   is shut down. Often the entries there are just copies or a subset 
 +#   from the respective start tag.
 +# * Should-Start/Stop are now part of LSB as of 2.0,
 +#   formerly SUSE/Unitedlinux used X-UnitedLinux-Should-Start/-Stop.
 +#   insserv does support both variants.
 +# * X-UnitedLinux-Default-Enabled: yes/no is used at installation time
 +#   (%fillup_and_insserv macro in %post of many RPMs) to specify whether
 +#   a startup script should default to be enabled after installation.
 +#   It's not used by insserv.
 +#
 +# Note on runlevels:
 +# 0 - halt/poweroff 6 - reboot
 +# 1 - single user 2 - multiuser without network exported
 +# 3 - multiuser w/ network (text mode)  5 - multiuser w/ network and X11 (xdm)
 +
 +# Note on script names:
 +# http://www.linuxbase.org/spec/refspecs/LSB_1.3.0/gLSB/gLSB/scrptnames.html
 +# A registry has been set up to manage the init script namespace.
 +# http://www.lanana.org/
 +# Please use the names already registered or register one or use a
 +# vendor prefix.
 +
 +TOMCAT_HOME=/usr/local/share/tomcat
 +test -d $TOMCAT_HOME || { echo "$TOMCAT_HOME is not a directory. Please check." 
 +;
 + if [ "$1" = "stop" ]; then exit 0;
 + else exit 5; fi; }
 +# Check for missing binaries (stale symlinks should not happen)
 +# Note: Special treatment of stop for LSB conformance
 +TOMCAT_BIN=$TOMCAT_HOME/lib/catalina.jar
 +test -s $TOMCAT_BIN || { echo "$TOMCAT_BIN not found. Is tomcat properly install
 +ed?"; 
 + if [ "$1" = "stop" ]; then exit 0;
 + else exit 5; fi; }
 +
 +# Check for existence of needed config file and read it
 +TOMCAT_CONFIG=$TOMCAT_HOME/conf/server.xml
 +test -r $TOMCAT_CONFIG || { echo "$TOMCAT_CONFIG not exists or not readable";
 + if [ "$1" = "stop" ]; then exit 0;
 + else exit 6; fi; }
 +
 +# Source LSB init functions
 +# providing start_daemon, killproc, pidofproc, 
 +# log_success_msg, log_failure_msg and log_warning_msg.
 +# This is currently not used by UnitedLinux based distributions and
 +# not needed for init scripts for UnitedLinux only. If it is used,
 +# the functions from rc.status should not be sourced or used.
 +#. /lib/lsb/init-functions
 +
 +# Shell functions sourced from /etc/rc.status:
 +#      rc_check         check and set local and overall rc status
 +#      rc_status        check and set local and overall rc status
 +#      rc_status -v     be verbose in local rc status and clear it afterwards
 +#      rc_status -v -r  ditto and clear both the local and overall rc status
 +#      rc_status -s     display "skipped" and exit with status 3
 +#      rc_status -u     display "unused" and exit with status 3
 +#      rc_failed        set local and overall rc status to failed
 +#      rc_failed <num>  set local and overall rc status to <num>
 +#      rc_reset         clear both the local and overall rc status
 +#      rc_exit          exit appropriate to overall rc status
 +#      rc_active        checks whether a service is activated by symlinks
 +. /etc/rc.status
 +
 +# Reset status of this service
 +rc_reset
 +
 +# Return values acc. to LSB for all commands but status:
 +# 0   - success
 +# 1       - generic or unspecified error
 +# 2       - invalid or excess argument(s)
 +# 3       - unimplemented feature (e.g. "reload")
 +# 4       - user had insufficient privileges
 +# 5       - program is not installed
 +# 6       - program is not configured
 +# 7       - program is not running
 +# 8--199  - reserved (8--99 LSB, 100--149 distrib, 150--199 appl)
 +
 +# Note that starting an already running service, stopping
 +# or restarting a not-running service as well as the restart
 +# with force-reload (in case signaling is not supported) are
 +# considered a success.
 +
 +case "$1" in
 +    start)
 + echo -n "Starting Tomcat "
 + ## Start daemon with startproc(8). If this fails
 + ## the return value is set appropriately by startproc.
 + #/sbin/startproc -u tomcat -g tomcat $TOMCAT_HOME/bin/startup.sh
 +
 + su tomcat -c $TOMCAT_HOME/bin/startup.sh
 +
 + # Remember status and be verbose
 + rc_status -v
 + ;;
 +    stop)
 + echo -n "Shutting down Tomcat "
 + ## Stop daemon with killproc(8) and if this fails
 + ## killproc sets the return value according to LSB.
 + #/sbin/startproc -u tomcat -g tomcat $TOMCAT_HOME/bin/shutdown.sh
 +
 + su tomcat -c $TOMCAT_HOME/bin/shutdown.sh
 +
 + # Remember status and be verbose
 + rc_status -v
 + ;;
 +    restart)
 + ## Stop the service and regardless of whether it was
 + ## running or not, start it again.
 + $0 stop
 + $0 start
 + # Remember status and be quiet
 + rc_status
 + ;;
 +    *)
 + echo "Usage: $0 {start|stop|restart}"
 + exit 1
 + ;;
 +esac
 +rc_exit
 +
 +
 +
 +
 +</code>
 +
 +
 +====== Integration with Apache ======
 +
 +Due to the fact that I am using apache at the same time in the same machine, Tomcat will act only as the server of the JSP pages, delegating all the static content to apache.
 +
 +You have to have ''apxs'' installed in your system. If you are running apache, it is achieved installing through yast the module ''apache2-devel''
 +
 +===== Tomcat connector mod-jk =====
 +
 +The only way to integrate apache with tomcat is to use mod_jk. Here is the documentation: 
 +
 +[[http://tomcat.apache.org/connectors-doc/webserver_howto/apache.html]]
 +
 +And you have to google the download location. I've downloaded the source code and here are the instructions to compile it: 
 +
 +==== Installing and compiling mod_jk ====
 +
 +Once you have the apxs2 program installed and the source code of the mod_jk, you are prepared to compile it: 
 +
 +<code>
 +$ cd native 
 +$ ./configure --with-apxs=/usr/sbin/apxs2
 +$ su
 +# make install
 +</code>
 +
 +http://tomcat.apache.org/connectors-doc-archive/jk2/jk/quickhowto.html
 +
 +
 +
 +===== Things to do in apache =====
 +
 +In the apache configuration directory, create a file called "workers.properties" with the following content: 
 +
 +<code>
 +# Define 1 real worker using ajp13
 +worker.list=worker1
 +# Set properties for worker1 (ajp13)
 +worker.worker1.type=ajp13
 +worker.worker1.host=localhost
 +worker.worker1.port=8009
 +worker.worker1.lbfactor=50
 +worker.worker1.cachesize=10
 +worker.worker1.cache_timeout=600
 +worker.worker1.socket_keepalive=1
 +worker.worker1.socket_timeout=300 
 +</code>
 +
 +At least the following configuration must be put under apache:
 +
 +
 +<code>
 +# Load mod_jk module
 +# Under SuSE this is carried out by sysconfig/apache2
 +# Update this path to match your modules location
 +LoadModule jk_module libexec/mod_jk.so
 +
 +# Under SuSE this is carried out by sysconfig/apache2
 +# Declare the module for <IfModule directive>
 +AddModule mod_jk.c
 +
 +# Where to find workers.properties
 +# Update this path to match your conf directory location (put workers.properties next to httpd.conf)
 +JkWorkersFile /etc/httpd/conf/workers.properties
 +
 +# Where to put jk logs
 +# Update this path to match your logs directory location (put mod_jk.log next to access_log)
 +JkLogFile /var/log/httpd/mod_jk.log
 +
 +# Set the jk log level [debug/error/info]
 +JkLogLevel info
 +
 +# Select the log format
 +JkLogStampFormat "[%a %b %d %H:%M:%S %Y] "
 +
 +# JkOptions indicate to send SSL KEY SIZE,
 +JkOptions +ForwardKeySize +ForwardURICompat -ForwardDirectories
 +
 +# JkRequestLogFormat set the request format
 +JkRequestLogFormat "%w %V %T"
 +
 +# Send everything for context /examples to worker named worker1 (ajp13)
 +JkMount /examples/* worker1
 +
 +# In installation with virtual servers, it allows to respond to 
 +# http://wateverthedomainwillbe/examples 
 +# If not, you have to put this directive (JkMountCopy) under 
 +# the VirtualHost directive you want to use 
 +JkMountCopy All
 +
 +</code>
 +
 +There are several ways to organize it. Under SuSE, the best way is the following: 
 +
 +  * under ''/etc/sysconfig/apache2'' modify the line ''APACHE_MODULES'' and add at the end the "jk": this will instruct to load the mod_jk.so module also and modify /etc/apache2/sysconfig/loadmodule.conf according to that
 +  * also modify the variable ''APACHE_CONF_INCLUDE_FILES'' to include a file that will be called ''mod_jk.conf''
 +  * create the file /etc/apache2/mod_jk.conf to include the configuration proper to the mod_jk.so module. Please add <IfModule mod_jk.c>  and </IfModule> directives to better exclude by simply removing the module from loading 
 +
 +
 +====== Security Issues ======
 +
 +===== Deactivate the listening through the 8080 port =====
 +
 +
 +Disconnect the default Connector port under tomcat: the port 8080. If you aren't gonna use it, the obvious is to disconnect it. 
 +
 +Under TOMCAT_HOME, locate the file server.xml and comment out the following lines: 
 +
 +<code xml>
 +    <!-- Connector port="8080" protocol="HTTP/1.1" 
 +               connectionTimeout="20000" 
 +               redirectPort="8443" / -->
 +
 +</code>
 +
 +===== Delete the "examples" application =====
 +
 +Go to TOMCAT_HOME/webapps and delete the directory "examples". Why? Because is a well-known application that **do** things. Some example applications aren't built with security in mind, so it is a good idea to delete them. 
 +
 +====== Test and conclusion ======
 +
 +Test, test, test... In every step you take in this issue, try to test if you are doing the correct!!! This is the best advice I can give you in order to succeed in such projects. 
 +
 +Anyway, the last step is to test the issue. I've opened a browser, point it to http://mydomain.com/examples/whateveryouwant and you should have a fantastic error screen directly from tomcat (instead of a 404 coming from apache). 
 +
 +{{ :java:screenshot_at_2011-11-13_16:43:53.png?200 |}}
 +
 +
 +You can elaborate this much --as I did-- and change the "examples" you find in the mod_jk.conf file for "docs": this will point to an application called "docs" that is in Tomcat. If you do this, you cant point your browser to http://mydomain.com/docs/index.html and get the tomcat documentation that comes with the tomcat installation: 
 +
 +
 +{{ :java:screenshot_at_2011-11-13_16:47:09.png?200 |}}
 +
 +===== Conclusion =====
 +
 +
 +In this document I've tried to explain how to install tomcat to serve as a backend for an Apache http server, so it serves only certain types of pages. 
 +
 +The explanation is made from the ground, as if there were no prior knowledge of apache nor tomcat. I hope I achieved this. If not, drop me some lines in the Discussion below. Anyway, any comment or suggestion will help. 
 +
 +====== Documentation ======
 +
 +I checked out this document: [[http://www.digitalsanctum.com/2007/08/18/20-tips-for-using-tomcat-in-production/]]. Unless it is a bit outdated (2007), many of the ideas depicted there are still valid.
 +
 +Of course, I checked also the Apache Tomcat documentation: [[http://tomcat.apache.org/tomcat-7.0-doc/index.html]]
 +
 +And have a look at this: [[http://tomcat.apache.org/connectors-doc/reference/apache.html]]. It is the documentation of the mod_jk module and it is very important if you want to have your own installation.
 +
 +~~DISQUS~~
 +
 +
 + 
java/installationunderlinux.txt · Last modified: 2022/12/02 22:02 by 127.0.0.1