Issue
We have common configuration for log4j2.xml
under catalina
base directory. so all the modules under webapps
use this configuration. Also log4j-core
, log4j-web
and log4j-api
libraries under shared lib of tomcat. When we restart the tomcat all the modules wrote their logs. But when redeploy any of them only that module logs others not. For example we have A
,B
and C
module under the webapps folder. If we redeploy C
module after restart then we see only C
module logs. How can I solve this problem? I could not found any reson why this happen
I enabled the log4j
logs to see what is happening. After redeploy log4j
print this kind of logs
2021-04-13 17:40:56,930 Catalina-utility-1 DEBUG Registering MBean org.apache.logging.log4j2:type=457e2f02
2021-04-13 17:40:56,930 Catalina-utility-1 DEBUG Registering MBean org.apache.logging.log4j2:type=457e2f02,component=StatusLogger
2021-04-13 17:40:56,930 Catalina-utility-1 DEBUG Registering MBean org.apache.logging.log4j2:type=457e2f02,component=ContextSelector
2021-04-13 17:40:56,930 Catalina-utility-1 DEBUG Registering MBean org.apache.logging.log4j2:type=457e2f02,component=Loggers,name=
457e2f02
this should be the our module name but why log4j
print random text
log4j2.xml
<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="DEBUG" monitoring="10">
<Properties>
<Property name="log.level">ALL</Property>
<Property name="framework.log.level">WARN</Property>
<Property name="file.pattern">%d{DEFAULT}: [%level{WARN=WAR, DEBUG=DBG, ERROR=ERR, TRACE=TRC, INFO=INF, FATAL=FTL}] %-c.%M[%L] - %m%n</Property>
<Property name="console.pattern">%highlight{%d{DEFAULT}: [%level{WARN=WAR, DEBUG=DBG, ERROR=ERR, TRACE=TRC, INFO=INF, FATAL=FTL}] %-c.%M[%L] - %m%n \n}{FATAL=red blink, ERROR=red bold, WARN=yellow bold, INFO=green bold, DEBUG=white bold, TRACE=cyan}</Property>
<Property name="logs.dir">logs</Property>
<Property name="app.name">magus</Property>
<Property name="script.test.mode">false</Property>
</Properties>
<Appenders>
<Console name="CONSOLE" target="SYSTEM_OUT">
<PatternLayout pattern="${console.pattern}"/>
</Console>
<Socket name="GELF" protocol="tcp" host="graylog.host" port="12201">
<!-- gelf tcp does not support compression-->
<GelfLayout includeStackTrace="true" host="${hostName}" includeThreadContext="true" includeNullDelimiter="true"
compressionType="OFF">
<KeyValuePair key="host" value="${hostName}"/>
<KeyValuePair key="version" value="1.1"/>
<!--<KeyValuePair key="short_message" value="$${event:Message}"/>--><!-- not required -->
<!--<KeyValuePair key="application_name" value="$${ctx:application}"/>-->
<KeyValuePair key="thread_id" value="$${event:ThreadId}"/>
<KeyValuePair key="thread_name" value="$${event:ThreadName}"/>
<KeyValuePair key="timestamp" value="$${event:Timestamp}"/>
<!--<KeyValuePair key="level" value="1"/>--><!-- default level type is number so we don't use-->
<KeyValuePair key="log_level" value="$${event:Level}"/><!-- for readabilty and filtering-->
</GelfLayout>
</Socket>
<RollingFile name="LOG" fileName="${logs.dir}/${app.name}.log"
filePattern="${logs.dir}/$${date:yyyy-MM}/${app.name}-%d{yyyy-MM-dd}.log.gz">
<PatternLayout pattern="${file.pattern}"/>
<Policies>
<TimeBasedTriggeringPolicy/>
</Policies>
<DefaultRolloverStrategy max="3">
<!--
Nested conditions: the inner condition is only evaluated on files
for which the outer conditions are true.
-->
<Delete basePath="${logs.dir}" maxDepth="2" testMode="${script.test.mode}">
<IfFileName glob="*/${app.name}*.log.gz">
<IfLastModified age="90d">
<IfAny>
<IfAccumulatedFileCount exceeds="10"/>
</IfAny>
</IfLastModified>
</IfFileName>
</Delete>
</DefaultRolloverStrategy>
</RollingFile>
</Appenders>
<Loggers>
<Root level="INFO">
<AppenderRef ref="CONSOLE"/>
<AppenderRef ref="LOG"/>
<AppenderRef ref='GELF' />
</Root>
<Logger name="xxx.project" level="${log.level}"/>
<Logger name="org.hibernate" level="${framework.log.level}"/>
<Logger name="com.zaxxer" level="${framework.log.level}"/>
<!--<Logger name="org.hibernate" level="ALL"/>-->
<Logger name="org.reflections" level="OFF"/>
<!-- show executed queries -->
<!--<Logger name="org.hibernate.SQL" level="DEBUG"/>-->
<!-- show query params -->
<!--
<Logger name="org.hibernate.type.descriptor.sql" level="TRACE"/> -->
<!--
<AsyncLogger name="az.sanco.projects.ais.server.filter" additivity="false" level="${log.level}">
<AppenderRef ref="AUDITOR"/>
</AsyncLogger> -->
</Loggers>
</Configuration>
Tomcat version: 9.0
Java version: 1.8
log4j2 version: 2.14.0
Solution
The random name 457e2f02
of your LoggerContext
suggests that all your applications are using a single context. When one of your applications is stopped, the stop
method is called on the context and no further messages can be logged. Meanwhile the reloaded application creates a context for itself.
This can occur, if you are using the Log4j API directly in your applications, but you don't ship the applications with a copy of log4j-api
: in this situation the LogManager
class in the shared Tomcat classloader will be used by all applications.
Try adding log4j-api.jar
to your applications.
Answered By - Piotr P. Karwasz