tomcat9

tomcat 9 second instance logging to default catalina.out location


On my debian server I have multiple tomcat installations. With version 8 this worked 100% now I'm upgrading to version 9 and the second instance of tomcat is logging to the default catalina.out file. I would like it to log to its own location. I tried to change the logging in logging.proprties but that seems not to work. The localhost and catalina rollover logs are in the right place, so the second instance has its own.

Here is my logging.properties of my second instance:

1catalina.org.apache.juli.AsyncFileHandler.level = FINE
1catalina.org.apache.juli.AsyncFileHandler.directory = ${catalina.base}/logs
1catalina.org.apache.juli.AsyncFileHandler.prefix = catalina.
1catalina.org.apache.juli.AsyncFileHandler.maxDays = 90

2localhost.org.apache.juli.AsyncFileHandler.level = FINE
2localhost.org.apache.juli.AsyncFileHandler.directory = ${catalina.base}/logs
2localhost.org.apache.juli.AsyncFileHandler.prefix = localhost.
2localhost.org.apache.juli.AsyncFileHandler.maxDays = 90

java.util.logging.ConsoleHandler.level = FINE
java.util.logging.ConsoleHandler.formatter = org.apache.juli.SystemdFormatter

I tried adding:

java.util.logging.ConsoleHandler.directory = ${catalina.base}/logs

But that did not seem to help.

So anyone knows how to config the location so the catalina.out goes to the catalina.base/logs location?

In reaction to question: I have installed tomcat9 with apt install tomcat9 and the instance with tomcat9-instance-create -c 8009 staging

This is my tomcat9_staging.service to startup with service tomcat9_staging start/restart

#
# Systemd unit file for Apache Tomcat
#

[Unit]
Description=Apache Tomcat 9 Web Application Server - For Staging
Documentation=https://tomcat.apache.org/tomcat-9.0-doc/index.html
After=network.target
RequiresMountsFor=/var/log/tomcat9 /var/lib/tomcat9

[Service]

# Configuration
Environment="CATALINA_HOME=/usr/share/tomcat9"
Environment="CATALINA_BASE=/app/tomcat9/staging"
Environment="CATALINA_TMPDIR=/tmp"
Environment="JAVA_OPTS=-Djava.awt.headless=true"

# Lifecycle
Type=simple
ExecStartPre=+/usr/libexec/tomcat9/tomcat-update-policy.sh
ExecStart=/bin/sh /usr/libexec/tomcat9/tomcat-start.sh
SuccessExitStatus=143
Restart=on-abort

# Logging
SyslogIdentifier=tomcat9_staging

# Security
User=tomcat
Group=tomcat
PrivateTmp=yes
AmbientCapabilities=CAP_NET_BIND_SERVICE
NoNewPrivileges=true
CacheDirectory=tomcat9_staging
CacheDirectoryMode=750
ProtectSystem=strict
ReadWritePaths=/app/tomcat9/staging/
ReadWritePaths=/etc/tomcat9/Catalina/
ReadWritePaths=/var/lib/tomcat9/webapps/
ReadWritePaths=/var/log/tomcat9/

[Install]
WantedBy=multi-user.target

the tomcat-start.sh:

#!/bin/sh
#
# Startup script for Apache Tomcat with systemd
#

set -e

# Load the service settings
. /etc/default/tomcat9

# Find the Java runtime and set JAVA_HOME
. /usr/libexec/tomcat9/tomcat-locate-java.sh

# Set the JSP compiler if configured in the /etc/default/tomcat9 file
[ -n "$JSP_COMPILER" ] && JAVA_OPTS="$JAVA_OPTS -Dbuild.compiler=\"$JSP_COMPILER\""

export JAVA_OPTS

# Enable the Java security manager?
SECURITY=""
[ "$SECURITY_MANAGER" = "true" ] && SECURITY="-security"


# Start Tomcat
cd $CATALINA_BASE && exec $CATALINA_HOME/bin/catalina.sh run $SECURITY

The problem seems to be that the startup script runs tomcat with run and not with start.

there is a diff between start and run. with start the eval will be:

eval $_NOHUP "\"$_RUNJAVA\"" "\"$LOGGING_CONFIG\"" $LOGGING_MANAGER "$JAVA_OPTS" "$CATALINA_OPTS" \
  -D$ENDORSED_PROP="\"$JAVA_ENDORSED_DIRS\"" \
  -classpath "\"$CLASSPATH\"" \
  -Djava.security.manager \
  -Djava.security.policy=="\"$CATALINA_BASE/policy/catalina.policy\"" \
  -Dcatalina.base="\"$CATALINA_BASE\"" \
  -Dcatalina.home="\"$CATALINA_HOME\"" \
  -Djava.io.tmpdir="\"$CATALINA_TMPDIR\"" \
  org.apache.catalina.startup.Bootstrap "$@" start \
  >> "$CATALINA_OUT" 2>&1 "&"

with run:

eval exec "\"$_RUNJAVA\"" "\"$LOGGING_CONFIG\"" $LOGGING_MANAGER "$JAVA_OPTS" "$CATALINA_OPTS" \
  -D$ENDORSED_PROP="\"$JAVA_ENDORSED_DIRS\"" \
  -classpath "\"$CLASSPATH\"" \
  -Djava.security.manager \
  -Djava.security.policy=="\"$CATALINA_BASE/policy/catalina.policy\"" \
  -Dcatalina.base="\"$CATALINA_BASE\"" \
  -Dcatalina.home="\"$CATALINA_HOME\"" \
  -Djava.io.tmpdir="\"$CATALINA_TMPDIR\"" \
  org.apache.catalina.startup.Bootstrap "$@" start

Not sure what the idea behind this is but the result is a diff in where the logging goes.

My problem now is that via the service it will not startup with start only with run

So why is run not setup to log the same as start is ?


Solution

  • java.util.logging.ConsoleHandler.directory = ${catalina.base}/logs did not work,. because ConsoleLogger always logs to console, so setting on directory is meaningless.

    catalina.out is created by a redirect in catalina.sh as explained in the answer to this question. It's possible that the contents of this file have changed between Tomcat 8 and 9. You should check and edit it as needed.

    Edit:

    I think I know what’s going on. The script used by your setup to start Tomcat calls catalina.sh run.

    According to the source code for Tomcat 9.x if you start Tomcat that way system variable CATALINA_OUT is ignored and the output is sent to standard output and standard error files.

    Change run to start and it should work the way you want it to and create file catalina.out in the specified directory.

    Edit 2:

    I found this article about running Tomcat using systemd and this question about using systemd directly to redirect stdout and stderr to files. I hope they'll prove helpful.

    Redirecting can be as simple as adding this:

    StandardOutput=append:/app/log/tomcat9_staging_catalina.out
    StandardError=append:/app/log/tomcat9_staging_error.out
    ReadWritePaths=/app/log/
    

    to: /lib/systemd/system/tomcat9_staging.service