SOLR-7887: Upgrade Solr to use log4j2 -- log4j 1 now officially end of life

This commit is contained in:
Erick Erickson 2018-03-25 19:16:09 -07:00
parent 4bb02d8689
commit 624d128b5e
78 changed files with 1820 additions and 662 deletions

View File

@ -187,7 +187,8 @@
<property name="javadoc.noindex" value="true"/>
<property name="javadoc.doclint.args" value="-Xdoclint:all -Xdoclint:-missing"/>
<property name="javac.doclint.args" value="-Xdoclint:all/protected -Xdoclint:-missing"/>
<!---proc:none was added because of LOG4J2-1925 / JDK-8186647 -->
<property name="javac.doclint.args" value="-Xdoclint:all/protected -Xdoclint:-missing -proc:none"/>
<!-- Javadoc classpath -->
<path id="javadoc.classpath">

View File

@ -32,6 +32,7 @@ com.fasterxml.jackson.core.version = 2.5.4
/com.healthmarketscience.jackcess/jackcess = 2.1.8
/com.healthmarketscience.jackcess/jackcess-encrypt = 2.1.4
/com.ibm.icu/icu4j = 59.1
/com.lmax/disruptor = 3.4.0
/com.pff/java-libpst = 0.8.1
com.rometools.version = 1.5.1
@ -84,8 +85,9 @@ io.prometheus.version = 0.2.0
/junit/junit = 4.10
# NOTE: split out from the full version to also use as solr-ref-guide attribute
org.log4j.major.version = 1.2
/log4j/log4j = ${org.log4j.major.version}.17
org.log4j.major.version = 2.11
org.log4j.minor.version = 0
org.apache.logging.log4j.version = ${org.log4j.major.version}.${org.log4j.minor.version}
/mecab/mecab-ipadic = 2.7.0-20070801
/mecab/mecab-naist-jdic = 0.6.3b-20111013
@ -180,6 +182,11 @@ org.apache.james.apache.mime4j.version = 0.8.1
/org.apache.james/apache-mime4j-core = ${org.apache.james.apache.mime4j.version}
/org.apache.james/apache-mime4j-dom = ${org.apache.james.apache.mime4j.version}
/org.apache.logging.log4j/log4j-1.2-api = ${org.apache.logging.log4j.version}
/org.apache.logging.log4j/log4j-api = ${org.apache.logging.log4j.version}
/org.apache.logging.log4j/log4j-core = ${org.apache.logging.log4j.version}
/org.apache.logging.log4j/log4j-slf4j-impl = ${org.apache.logging.log4j.version}
/org.apache.mina/mina-core = 2.0.0-M5
/org.apache.opennlp/opennlp-maxent = 3.0.3
@ -301,7 +308,6 @@ org.slf4j.version = 1.7.24
/org.slf4j/jcl-over-slf4j = ${org.slf4j.version}
/org.slf4j/jul-to-slf4j = ${org.slf4j.version}
/org.slf4j/slf4j-api = ${org.slf4j.version}
/org.slf4j/slf4j-log4j12 = ${org.slf4j.version}
/org.slf4j/slf4j-simple = ${org.slf4j.version}
/org.tallison/jmatio = 1.2

View File

@ -166,6 +166,9 @@ Upgrade Notes
from the earlier default of 30 seconds. This affects how soon Solr adds new replicas to replace the replicas
on nodes which have either crashed or shutdown.
* SOLR-7887: Solr now uses Log4J 2.10. The log4j configuration is now in log4j2.xml rather than lo4j.properties
files (Shawn Heisey, Keith Laban, Timothy Potter, Varun Thacker, Erick Erickson,
New Features
----------------------
* SOLR-11285: Simulation framework for autoscaling. (ab)
@ -489,6 +492,8 @@ Other Changes
* SOLR-12097: Document the diskType policy attribute and usage of disk space in Collection APIs.
(Cassandra Targett, shalin)
* SOLR-7887: Upgrade Solr to Log4J 2.10 (Tim Potter, Keith Laban, Shawn Heisey, Ralph Goers, Varun Thacker)
================== 7.2.1 ==================
Consult the LUCENE_CHANGES.txt file for additional, low level, changes in this release.

View File

@ -326,7 +326,7 @@ else
mv "$SOLR_INSTALL_DIR/bin/solr.in.cmd" "$SOLR_INSTALL_DIR/bin/solr.in.cmd.orig"
echo "SOLR_PID_DIR=\"$SOLR_VAR_DIR\"
SOLR_HOME=\"$SOLR_VAR_DIR/data\"
LOG4J_PROPS=\"$SOLR_VAR_DIR/log4j.properties\"
LOG4J_PROPS=\"$SOLR_VAR_DIR/log4j2.xml\"
SOLR_LOGS_DIR=\"$SOLR_VAR_DIR/logs\"
SOLR_PORT=\"$SOLR_PORT\"
" >> "/etc/default/$SOLR_SERVICE.in.sh"
@ -342,10 +342,10 @@ if [ -f "$SOLR_VAR_DIR/data/solr.xml" ]; then
else
cp "$SOLR_INSTALL_DIR/server/solr/"{solr.xml,zoo.cfg} "$SOLR_VAR_DIR/data/"
fi
if [ -f "$SOLR_VAR_DIR/log4j.properties" ]; then
echo -e "\n$SOLR_VAR_DIR/log4j.properties already exists. Skipping install ...\n"
if [ -f "$SOLR_VAR_DIR/log4j2.xml" ]; then
echo -e "\n$SOLR_VAR_DIR/log4j2.xml already exists. Skipping install ...\n"
else
cp "$SOLR_INSTALL_DIR/server/resources/log4j.properties" "$SOLR_VAR_DIR/log4j.properties"
cp "$SOLR_INSTALL_DIR/server/resources/log4j2.xml" "$SOLR_VAR_DIR/log4j2.xml"
fi
chown -R "$SOLR_USER:" "$SOLR_VAR_DIR"
find "$SOLR_VAR_DIR" -type d -print0 | xargs -0 chmod 0750

View File

@ -681,7 +681,7 @@ function jetty_port() {
function run_tool() {
"$JAVA" $SOLR_SSL_OPTS $AUTHC_OPTS $SOLR_ZK_CREDS_AND_ACLS -Dsolr.install.dir="$SOLR_TIP" \
-Dlog4j.configuration="file:$DEFAULT_SERVER_DIR/scripts/cloud-scripts/log4j.properties" \
-Dlog4j.configurationFile="file:$DEFAULT_SERVER_DIR/scripts/cloud-scripts/log4j2.xml" \
-classpath "$DEFAULT_SERVER_DIR/solr-webapp/webapp/WEB-INF/lib/*:$DEFAULT_SERVER_DIR/lib/ext/*" \
org.apache.solr.util.SolrCLI "$@"
@ -1783,20 +1783,20 @@ if [ -z "$DEFAULT_CONFDIR" ]; then
DEFAULT_CONFDIR="$SOLR_SERVER_DIR/solr/configsets/_default/conf"
fi
# This is quite hacky, but examples rely on a different log4j.properties
# This is quite hacky, but examples rely on a different log4j2.xml
# so that we can write logs for examples to $SOLR_HOME/../logs
if [ -z "$SOLR_LOGS_DIR" ]; then
SOLR_LOGS_DIR="$SOLR_SERVER_DIR/logs"
fi
EXAMPLE_DIR="$SOLR_TIP/example"
if [ "${SOLR_HOME:0:${#EXAMPLE_DIR}}" = "$EXAMPLE_DIR" ]; then
LOG4J_PROPS="$EXAMPLE_DIR/resources/log4j.properties"
LOG4J_PROPS="$EXAMPLE_DIR/resources/log4j2.xml"
SOLR_LOGS_DIR="$SOLR_HOME/../logs"
fi
LOG4J_CONFIG=()
if [ -n "$LOG4J_PROPS" ]; then
LOG4J_CONFIG+=("-Dlog4j.configuration=file:$LOG4J_PROPS")
LOG4J_CONFIG+=("-Dlog4j.configurationFile=file:$LOG4J_PROPS")
fi
if [ "$SCRIPT_CMD" == "stop" ]; then

View File

@ -935,7 +935,7 @@ IF NOT EXIST "%SOLR_HOME%\" (
IF "%STOP_KEY%"=="" set STOP_KEY=solrrocks
@REM This is quite hacky, but examples rely on a different log4j.properties
@REM This is quite hacky, but examples rely on a different log4j2.xml
@REM so that we can write logs for examples to %SOLR_HOME%\..\logs
IF [%SOLR_LOGS_DIR%] == [] (
set "SOLR_LOGS_DIR=%SOLR_SERVER_DIR%\logs"
@ -949,7 +949,7 @@ set "EXAMPLE_DIR=%SOLR_TIP%\example"
set TMP=!SOLR_HOME:%EXAMPLE_DIR%=!
IF NOT "%TMP%"=="%SOLR_HOME%" (
set "SOLR_LOGS_DIR=%SOLR_HOME%\..\logs"
set "LOG4J_CONFIG=file:%EXAMPLE_DIR%\resources\log4j.properties"
set "LOG4J_CONFIG=file:%EXAMPLE_DIR%\resources\log4j2.xml"
)
set IS_RESTART=0
@ -977,7 +977,7 @@ IF "%SCRIPT_CMD%"=="stop" (
IF "%%j"=="%SOLR_JETTY_HOST%:!SOME_SOLR_PORT!" (
set found_it=1
@echo Stopping Solr process %%k running on port !SOME_SOLR_PORT!
IF "%STOP_PORT%"=="" set /A STOP_PORT=!SOME_SOLR_PORT! - 1000
IF "%STOP_PORT%"=="" set /A STOP_PORT=!SOME_SOLR_PORT! - 1000
"%JAVA%" %SOLR_SSL_OPTS% -Djetty.home="%SOLR_SERVER_DIR%" -jar "%SOLR_SERVER_DIR%\start.jar" STOP.PORT=!STOP_PORT! STOP.KEY=%STOP_KEY% --stop
del "%SOLR_TIP%"\bin\solr-!SOME_SOLR_PORT!.port
timeout /T 5
@ -1007,7 +1007,7 @@ IF "%SCRIPT_CMD%"=="stop" (
IF "%%M"=="%SOLR_JETTY_HOST%:%SOLR_PORT%" (
set found_it=1
@echo Stopping Solr process %%N running on port %SOLR_PORT%
IF "%STOP_PORT%"=="" set /A STOP_PORT=%SOLR_PORT% - 1000
IF "%STOP_PORT%"=="" set /A STOP_PORT=%SOLR_PORT% - 1000
"%JAVA%" %SOLR_SSL_OPTS% -Djetty.home="%SOLR_SERVER_DIR%" -jar "%SOLR_SERVER_DIR%\start.jar" "%SOLR_JETTY_CONFIG%" STOP.PORT=!STOP_PORT! STOP.KEY=%STOP_KEY% --stop
del "%SOLR_TIP%"\bin\solr-%SOLR_PORT%.port
timeout /T 5
@ -1221,7 +1221,7 @@ IF "%SOLR_SSL_ENABLED%"=="true" (
IF NOT "%SOLR_LOG_LEVEL%"=="" set "START_OPTS=%START_OPTS% -Dsolr.log.level=%SOLR_LOG_LEVEL%"
set "START_OPTS=%START_OPTS% -Dsolr.log.dir=%SOLR_LOGS_DIR_QUOTED%"
IF NOT "%SOLR_DATA_HOME%"=="" set "START_OPTS=%START_OPTS% -Dsolr.data.home=%SOLR_DATA_HOME_QUOTED%"
IF NOT DEFINED LOG4J_CONFIG set "LOG4J_CONFIG=file:%SOLR_SERVER_DIR%\resources\log4j.properties"
IF NOT DEFINED LOG4J_CONFIG set "LOG4J_CONFIG=file:%SOLR_SERVER_DIR%\resources\log4j2.xml"
cd /d "%SOLR_SERVER_DIR%"
@ -1253,14 +1253,14 @@ IF "%FG%"=="1" (
title "Solr-%SOLR_PORT%"
echo %SOLR_PORT%>"%SOLR_TIP%"\bin\solr-%SOLR_PORT%.port
"%JAVA%" %SERVEROPT% %SOLR_JAVA_MEM% %START_OPTS% ^
-Dlog4j.configuration="%LOG4J_CONFIG%" -DSTOP.PORT=!STOP_PORT! -DSTOP.KEY=%STOP_KEY% ^
-Dlog4j.configurationFile="%LOG4J_CONFIG%" -DSTOP.PORT=!STOP_PORT! -DSTOP.KEY=%STOP_KEY% ^
-Dsolr.solr.home="%SOLR_HOME%" -Dsolr.install.dir="%SOLR_TIP%" -Dsolr.default.confdir="%DEFAULT_CONFDIR%" ^
-Djetty.host=%SOLR_JETTY_HOST% -Djetty.port=%SOLR_PORT% -Djetty.home="%SOLR_SERVER_DIR%" ^
-Djava.io.tmpdir="%SOLR_SERVER_DIR%\tmp" -jar start.jar "%SOLR_JETTY_CONFIG%" "%SOLR_JETTY_ADDL_CONFIG%"
) ELSE (
START /B "Solr-%SOLR_PORT%" /D "%SOLR_SERVER_DIR%" ^
"%JAVA%" %SERVEROPT% %SOLR_JAVA_MEM% %START_OPTS% ^
-Dlog4j.configuration="%LOG4J_CONFIG%" -DSTOP.PORT=!STOP_PORT! -DSTOP.KEY=%STOP_KEY% ^
-Dlog4j.configurationFile="%LOG4J_CONFIG%" -DSTOP.PORT=!STOP_PORT! -DSTOP.KEY=%STOP_KEY% ^
-Dsolr.log.muteconsole ^
-Dsolr.solr.home="%SOLR_HOME%" -Dsolr.install.dir="%SOLR_TIP%" -Dsolr.default.confdir="%DEFAULT_CONFDIR%" ^
-Djetty.host=%SOLR_JETTY_HOST% -Djetty.port=%SOLR_PORT% -Djetty.home="%SOLR_SERVER_DIR%" ^
@ -1269,7 +1269,7 @@ IF "%FG%"=="1" (
REM now wait to see Solr come online ...
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" -Dsolr.default.confdir="%DEFAULT_CONFDIR%"^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI status -maxWaitSecs 30 -solr !SOLR_URL_SCHEME!://%SOLR_TOOL_HOST%:%SOLR_PORT%/solr
)
@ -1280,7 +1280,7 @@ goto done
REM Run the requested example
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI run_example -script "%SDIR%\solr.cmd" -e %EXAMPLE% -d "%SOLR_SERVER_DIR%" ^
-urlScheme !SOLR_URL_SCHEME! !PASS_TO_RUN_EXAMPLE!
@ -1302,7 +1302,7 @@ for /f "usebackq" %%i in (`dir /b "%SOLR_TIP%\bin" ^| findstr /i "^solr-.*\.port
set has_info=1
echo Found Solr process %%k running on port !SOME_SOLR_PORT!
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI status -solr !SOLR_URL_SCHEME!://%SOLR_TOOL_HOST%:!SOME_SOLR_PORT!/solr
@echo.
@ -1349,14 +1349,14 @@ IF NOT DEFINED HEALTHCHECK_COLLECTION goto healthcheck_usage
IF NOT DEFINED HEALTHCHECK_VERBOSE set "HEALTHCHECK_VERBOSE="
IF NOT DEFINED HEALTHCHECK_ZK_HOST set "HEALTHCHECK_ZK_HOST=localhost:9983"
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI healthcheck -collection !HEALTHCHECK_COLLECTION! -zkHost !HEALTHCHECK_ZK_HOST! %HEALTHCHECK_VERBOSE%
goto done
:run_assert
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI %*
if errorlevel 1 (
@ -1366,7 +1366,7 @@ goto done
:run_config
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI %*
if errorlevel 1 (
@ -1376,7 +1376,7 @@ goto done
:get_version
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI version
goto done
@ -1386,7 +1386,7 @@ set "TOOL_CMD=%~1"
set q="-q"
IF "%verbose%"=="1" set q=""
"%JAVA%" %SOLR_SSL_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI utils -s "%DEFAULT_SERVER_DIR%" -l "%SOLR_LOGS_DIR%" %q:"=% %TOOL_CMD%
if errorlevel 1 (
@ -1492,13 +1492,13 @@ if "!CREATE_CONFDIR!"=="_default" (
if "%SCRIPT_CMD%"=="create_core" (
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI create_core -name !CREATE_NAME! -solrUrl !SOLR_URL_SCHEME!://%SOLR_TOOL_HOST%:!CREATE_PORT!/solr ^
-confdir !CREATE_CONFDIR! -configsetsDir "%SOLR_TIP%\server\solr\configsets" %CREATE_VERBOSE%
) else (
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" -Dsolr.default.confdir="%DEFAULT_CONFDIR%"^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI create -name !CREATE_NAME! -shards !CREATE_NUM_SHARDS! -replicationFactor !CREATE_REPFACT! ^
-confname !CREATE_CONFNAME! -confdir !CREATE_CONFDIR! -configsetsDir "%SOLR_TIP%\server\solr\configsets" ^
@ -1573,7 +1573,7 @@ if "!DELETE_CONFIG!"=="" (
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI delete -name !DELETE_NAME! -deleteConfig !DELETE_CONFIG! ^
-solrUrl !SOLR_URL_SCHEME!://%SOLR_TOOL_HOST%:!DELETE_PORT!/solr %DELETE_VERBOSE%
@ -1709,7 +1709,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -confname !CONFIGSET_NAME! -confdir !CONFIGSET_DIR! -zkHost !ZK_HOST! %ZK_VERBOSE%^
-configsetsDir "%SOLR_TIP%/server/solr/configsets"
@ -1723,7 +1723,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -confname !CONFIGSET_NAME! -confdir !CONFIGSET_DIR! -zkHost !ZK_HOST! %ZK_VERBOSE%
) ELSE IF "!ZK_OP!"=="cp" (
@ -1742,7 +1742,7 @@ IF "!ZK_OP!"=="upconfig" (
)
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -zkHost !ZK_HOST! -src !ZK_SRC! -dst !ZK_DST! -recurse !ZK_RECURSE! %ZK_VERBOSE%
) ELSE IF "!ZK_OP!"=="mv" (
@ -1755,7 +1755,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -zkHost !ZK_HOST! -src !ZK_SRC! -dst !ZK_DST! %ZK_VERBOSE%
) ELSE IF "!ZK_OP!"=="rm" (
@ -1764,7 +1764,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -zkHost !ZK_HOST! -path !ZK_SRC! -recurse !ZK_RECURSE! %ZK_VERBOSE%
) ELSE IF "!ZK_OP!"=="ls" (
@ -1773,7 +1773,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -zkHost !ZK_HOST! -path !ZK_SRC! -recurse !ZK_RECURSE! %ZK_VERBOSE%
) ELSE IF "!ZK_OP!"=="mkroot" (
@ -1782,7 +1782,7 @@ IF "!ZK_OP!"=="upconfig" (
goto zk_short_usage
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI !ZK_OP! -zkHost !ZK_HOST! -path !ZK_SRC! %ZK_VERBOSE%
) ELSE (
@ -1843,7 +1843,7 @@ if "!AUTH_PORT!"=="" (
)
)
"%JAVA%" %SOLR_SSL_OPTS% %AUTHC_OPTS% %SOLR_ZK_CREDS_AND_ACLS% -Dsolr.install.dir="%SOLR_TIP%" ^
-Dlog4j.configuration="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j.properties" ^
-Dlog4j.configurationFile="file:%DEFAULT_SERVER_DIR%\scripts\cloud-scripts\log4j2.xml" ^
-classpath "%DEFAULT_SERVER_DIR%\solr-webapp\webapp\WEB-INF\lib\*;%DEFAULT_SERVER_DIR%\lib\ext\*" ^
org.apache.solr.util.SolrCLI auth %AUTH_PARAMS% -solrIncludeFile "%SOLR_INCLUDE%" -authConfDir "%SOLR_HOME%" ^
-solrUrl !SOLR_URL_SCHEME!://%SOLR_TOOL_HOST%:!AUTH_PORT!/solr

View File

@ -78,7 +78,7 @@ REM If not set, defaults to <instance_dir>/data. Overridable per core through 'd
REM set SOLR_DATA_HOME=
REM Changes the logging level. Valid values: ALL, TRACE, DEBUG, INFO, WARN, ERROR, FATAL, OFF. Default is INFO
REM This is an alternative to changing the rootLogger in log4j.properties
REM This is an alternative to changing the rootLogger in log4j2.xml
REM set SOLR_LOG_LEVEL=INFO
REM Location where Solr should write logs to. Absolute or relative to solr start dir

View File

@ -93,13 +93,13 @@
# If not set, defaults to <instance_dir>/data. Overridable per core through 'dataDir' core property
#SOLR_DATA_HOME=
# Solr provides a default Log4J configuration properties file in server/resources
# Solr provides a default Log4J configuration xml file in server/resources
# however, you may want to customize the log settings and file appender location
# so you can point the script to use a different log4j.properties file
#LOG4J_PROPS=/var/solr/log4j.properties
# so you can point the script to use a different log4j2.xml file
#LOG4J_PROPS=/var/solr/log4j2.xml
# Changes the logging level. Valid values: ALL, TRACE, DEBUG, INFO, WARN, ERROR, FATAL, OFF. Default is INFO
# This is an alternative to changing the rootLogger in log4j.properties
# This is an alternative to changing the rootLogger in log4j2.xml
#SOLR_LOG_LEVEL=INFO
# Location where Solr should write logs to. Absolute or relative to solr start dir

View File

@ -1,10 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.solr.util.SolrLogLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %C; %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN

View File

@ -0,0 +1,37 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %c; %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="org.apache.hadoop" level="WARN"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -1,9 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.solr.util.SolrLogLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %C; %m%n
log4j.logger.org.apache.zookeeper=WARN

View File

@ -0,0 +1,36 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %c; %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -1,32 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
log4j.logger.org.apache.directory=WARN
log4j.logger.org.apache.solr.hadoop=INFO
log4j.logger.org.apache.solr.client.solrj.embedded.JettySolrRunner=DEBUG
org.apache.solr.client.solrj.embedded.JettySolrRunner=DEBUG
#log4j.logger.org.apache.solr.update.processor.LogUpdateProcessor=DEBUG
#log4j.logger.org.apache.solr.update.processor.DistributedUpdateProcessor=DEBUG
#log4j.logger.org.apache.solr.update.PeerSync=DEBUG
#log4j.logger.org.apache.solr.core.CoreContainer=DEBUG
#log4j.logger.org.apache.solr.cloud.RecoveryStrategy=DEBUG
#log4j.logger.org.apache.solr.cloud.SyncStrategy=DEBUG
#log4j.logger.org.apache.solr.handler.admin.CoreAdminHandler=DEBUG
#log4j.logger.org.apache.solr.cloud.ZkController=DEBUG
#log4j.logger.org.apache.solr.update.DefaultSolrCoreState=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ConnectionManager=DEBUG
#log4j.logger.org.apache.solr.update.UpdateLog=DEBUG
#log4j.logger.org.apache.solr.cloud.ChaosMonkey=DEBUG
#log4j.logger.org.apache.solr.update.TransactionLog=DEBUG
#log4j.logger.org.apache.solr.handler.ReplicationHandler=DEBUG
#log4j.logger.org.apache.solr.handler.IndexFetcher=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ClusterStateUtil=DEBUG
#log4j.logger.org.apache.solr.cloud.OverseerAutoReplicaFailoverThread=DEBUG

View File

@ -0,0 +1,41 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="org.apache.hadoop" level="WARN"/>
<Logger name="org.apache.directory" level="WARN"/>
<Logger name="org.apache.solr.hadoop" level="INFO"/>
<Logger name="log4j.logger.org.apache.solr.hadoop" level="INFO"/>
<Logger name="org.apache.solr.client.solrj.embedded.JettySolrRunner" level="DEBUG"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -32,8 +32,9 @@
<dependency org="net.thisptr" name="jackson-jq" rev="${/net.thisptr/jackson-jq}" conf="compile"/>
<dependency org="net.sourceforge.argparse4j" name="argparse4j" rev="${/net.sourceforge.argparse4j/argparse4j}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-api" rev="${/org.slf4j/slf4j-api}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-log4j12" rev="${/org.slf4j/slf4j-log4j12}" conf="compile"/>
<dependency org="log4j" name="log4j" rev="${/log4j/log4j}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-slf4j-impl" rev="${/org.apache.logging.log4j/log4j-slf4j-impl}" conf="test"/>
<dependency org="org.apache.logging.log4j" name="log4j-api" rev="${/org.apache.logging.log4j/log4j-api}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-core" rev="${/org.apache.logging.log4j/log4j-core}" conf="compile"/>
<exclude org="*" ext="*" matcher="regexp" type="${ivy.exclude.types}"/>
</dependencies>

View File

@ -47,8 +47,12 @@
<dependency org="joda-time" name="joda-time" rev="${/joda-time/joda-time}" conf="compile"/>
<dependency org="dom4j" name="dom4j" rev="${/dom4j/dom4j}" conf="compile"/>
<dependency org="com.carrotsearch" name="hppc" rev="${/com.carrotsearch/hppc}" conf="compile"/>
<dependency org="log4j" name="log4j" rev="${/log4j/log4j}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-log4j12" rev="${/org.slf4j/slf4j-log4j12}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-api" rev="${/org.apache.logging.log4j/log4j-api}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-core" rev="${/org.apache.logging.log4j/log4j-core}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-slf4j-impl" rev="${/org.apache.logging.log4j/log4j-slf4j-impl}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-1.2-api" rev="${/org.apache.logging.log4j/log4j-1.2-api}" conf="compile"/>
<dependency org="com.lmax" name="disruptor" rev="${/com.lmax/disruptor}" conf="compile"/>
<dependency org="org.slf4j" name="jcl-over-slf4j" rev="${/org.slf4j/jcl-over-slf4j}" conf="compile"/>
<dependency org="org.mockito" name="mockito-core" rev="${/org.mockito/mockito-core}" conf="test"/>

View File

@ -363,7 +363,7 @@ public class JettySolrRunner {
*
* If the server has been started before, it will restart using the same port
*
* @throws Exception if an error occurs on startup
* @throws java.lang.Exception if an error occurs on startup
*/
public void start() throws Exception {
start(true);

View File

@ -67,7 +67,7 @@ public class LoggingHandler extends RequestHandlerBase implements SolrCoreAware
@Override
public void handleRequestBody(SolrQueryRequest req, SolrQueryResponse rsp) throws Exception {
// Don't do anything if the framework is unknown
if(watcher==null) {
if (watcher==null) {
rsp.add("error", "Logging Not Initialized");
return;
}
@ -142,7 +142,7 @@ public class LoggingHandler extends RequestHandlerBase implements SolrCoreAware
Collections.sort(loggers);
List<SimpleOrderedMap<?>> info = new ArrayList<>();
for(LoggerInfo wrap:loggers) {
for (LoggerInfo wrap : loggers) {
info.add(wrap.getInfo());
}
rsp.add("loggers", info);

View File

@ -20,7 +20,7 @@ import org.apache.solr.common.SolrDocument;
import org.apache.solr.common.SolrDocumentList;
import org.apache.solr.core.SolrResourceLoader;
import org.apache.solr.logging.jul.JulWatcher;
import org.apache.solr.logging.log4j.Log4jWatcher;
import org.apache.solr.logging.log4j2.Log4j2Watcher;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.impl.StaticLoggerBinder;
@ -34,7 +34,7 @@ import java.util.concurrent.atomic.AtomicBoolean;
/**
* A Class to monitor Logging events and hold N events in memory
*
* This is abstract so we can support both JUL and Log4j (and other logging platforms)
* This is abstract so we can support both JUL and Log4j2 (and other logging platforms)
*/
public abstract class LogWatcher<E> {
@ -152,8 +152,8 @@ public abstract class LogWatcher<E> {
slf4jImpl = StaticLoggerBinder.getSingleton().getLoggerFactoryClassStr();
log.debug("SLF4J impl is " + slf4jImpl);
if (fname == null) {
if ("org.slf4j.impl.Log4jLoggerFactory".equals(slf4jImpl)) {
fname = "Log4j";
if ("org.apache.logging.slf4j.Log4jLoggerFactory".equals(slf4jImpl)) {
fname = "Log4j2";
} else if (slf4jImpl.indexOf("JDK") > 0) {
fname = "JUL";
}
@ -172,10 +172,12 @@ public abstract class LogWatcher<E> {
return null;
}
if ("JUL".equalsIgnoreCase(fname))
if ("JUL".equalsIgnoreCase(fname)) {
return new JulWatcher(slf4jImpl);
if ("Log4j".equals(fname))
return new Log4jWatcher(slf4jImpl);
}
if ("Log4j2".equals(fname)) {
return new Log4j2Watcher();
}
try {
return loader != null ? loader.newInstance(fname, LogWatcher.class) : null;

View File

@ -1,48 +0,0 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.solr.logging.log4j;
import org.apache.log4j.AppenderSkeleton;
import org.apache.log4j.spi.LoggingEvent;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.logging.LogWatcher;
@SuppressForbidden(reason = "class is specific to log4j")
public final class EventAppender extends AppenderSkeleton {
final LogWatcher<LoggingEvent> watcher;
public EventAppender(LogWatcher<LoggingEvent> framework) {
this.watcher = framework;
}
@Override
public void append( LoggingEvent event )
{
watcher.add(event,event.timeStamp);
}
@Override
public void close() {
watcher.reset();
}
@Override
public boolean requiresLayout() {
return false;
}
}

View File

@ -1,52 +0,0 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.solr.logging.log4j;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.logging.LoggerInfo;
@SuppressForbidden(reason = "class is specific to log4j")
public class Log4jInfo extends LoggerInfo {
final org.apache.log4j.Logger logger;
public Log4jInfo(String name, org.apache.log4j.Logger logger) {
super(name);
this.logger = logger;
}
@Override
public String getLevel() {
if(logger==null) {
return null;
}
Object level = logger.getLevel();
if(level==null) {
return null;
}
return level.toString();
}
@Override
public String getName() {
return name;
}
@Override
public boolean isSet() {
return (logger!=null && logger.getLevel()!=null);
}
}

View File

@ -1,171 +0,0 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.solr.logging.log4j;
import java.util.Arrays;
import java.util.Collection;
import java.util.Date;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.log4j.AppenderSkeleton;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.log4j.spi.LoggingEvent;
import org.apache.log4j.spi.ThrowableInformation;
import org.apache.solr.common.SolrDocument;
import org.apache.solr.common.cloud.ZkStateReader;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.logging.CircularList;
import org.apache.solr.logging.ListenerConfig;
import org.apache.solr.logging.LogWatcher;
import org.apache.solr.logging.LoggerInfo;
import com.google.common.base.Throwables;
@SuppressForbidden(reason = "class is specific to log4j")
public class Log4jWatcher extends LogWatcher<LoggingEvent> {
final String name;
AppenderSkeleton appender = null;
public Log4jWatcher(String name) {
this.name = name;
}
@Override
public String getName() {
return "Log4j ("+name+")";
}
@Override
public List<String> getAllLevels() {
return Arrays.asList(
org.apache.log4j.Level.ALL.toString(),
org.apache.log4j.Level.TRACE.toString(),
org.apache.log4j.Level.DEBUG.toString(),
org.apache.log4j.Level.INFO.toString(),
org.apache.log4j.Level.WARN.toString(),
org.apache.log4j.Level.ERROR.toString(),
org.apache.log4j.Level.FATAL.toString(),
org.apache.log4j.Level.OFF.toString());
}
@Override
public void setLogLevel(String category, String level) {
org.apache.log4j.Logger log;
if(LoggerInfo.ROOT_NAME.equals(category)) {
log = org.apache.log4j.LogManager.getRootLogger();
} else {
log = org.apache.log4j.Logger.getLogger(category);
}
if(level==null||"unset".equals(level)||"null".equals(level)) {
log.setLevel(null);
}
else {
log.setLevel(org.apache.log4j.Level.toLevel(level));
}
}
@Override
public Collection<LoggerInfo> getAllLoggers() {
org.apache.log4j.Logger root = org.apache.log4j.LogManager.getRootLogger();
Map<String,LoggerInfo> map = new HashMap<>();
Enumeration<?> loggers = org.apache.log4j.LogManager.getCurrentLoggers();
while (loggers.hasMoreElements()) {
org.apache.log4j.Logger logger = (org.apache.log4j.Logger)loggers.nextElement();
String name = logger.getName();
if( logger == root) {
continue;
}
map.put(name, new Log4jInfo(name, logger));
while (true) {
int dot = name.lastIndexOf(".");
if (dot < 0)
break;
name = name.substring(0, dot);
if(!map.containsKey(name)) {
map.put(name, new Log4jInfo(name, null));
}
}
}
map.put(LoggerInfo.ROOT_NAME, new Log4jInfo(LoggerInfo.ROOT_NAME, root));
return map.values();
}
@Override
public void setThreshold(String level) {
if(appender==null) {
throw new IllegalStateException("Must have an appender");
}
appender.setThreshold(Level.toLevel(level));
}
@Override
public String getThreshold() {
if(appender==null) {
throw new IllegalStateException("Must have an appender");
}
return appender.getThreshold().toString();
}
@Override
public void registerListener(ListenerConfig cfg) {
if(history!=null) {
throw new IllegalStateException("History already registered");
}
history = new CircularList<>(cfg.size);
appender = new EventAppender(this);
if(cfg.threshold != null) {
appender.setThreshold(Level.toLevel(cfg.threshold));
}
else {
appender.setThreshold(Level.WARN);
}
Logger log = org.apache.log4j.LogManager.getRootLogger();
log.addAppender(appender);
}
@Override
public long getTimestamp(LoggingEvent event) {
return event.timeStamp;
}
@Override
public SolrDocument toSolrDocument(LoggingEvent event) {
SolrDocument doc = new SolrDocument();
doc.setField("time", new Date(event.getTimeStamp()));
doc.setField("level", event.getLevel().toString());
doc.setField("logger", event.getLogger().getName());
doc.setField("message", event.getRenderedMessage());
ThrowableInformation t = event.getThrowableInformation();
if(t!=null) {
doc.setField("trace", Throwables.getStackTraceAsString(t.getThrowable()));
}
// Will be null if not present
doc.setField("core", event.getMDC(ZkStateReader.CORE_NAME_PROP));
doc.setField("collection", event.getMDC(ZkStateReader.COLLECTION_PROP));
doc.setField("replica", event.getMDC(ZkStateReader.REPLICA_PROP));
doc.setField("shard", event.getMDC(ZkStateReader.SHARD_ID_PROP));
return doc;
}
}

View File

@ -0,0 +1,289 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.solr.logging.log4j2;
import java.util.Arrays;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.core.Filter;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.AbstractAppender;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.logging.log4j.core.LogEvent;
import org.apache.logging.log4j.core.filter.ThresholdFilter;
import org.apache.logging.log4j.message.Message;
import org.apache.solr.common.SolrDocument;
import org.apache.solr.logging.CircularList;
import org.apache.solr.logging.ListenerConfig;
import org.apache.solr.logging.LogWatcher;
import org.apache.solr.logging.LoggerInfo;
import com.google.common.base.Throwables;
public class Log4j2Watcher extends LogWatcher<LogEvent> {
private final static String LOG4J2_WATCHER_APPENDER = "Log4j2WatcherAppender";
protected class Log4j2Appender extends AbstractAppender {
private Log4j2Watcher watcher;
private ThresholdFilter filter;
private Level threshold;
Log4j2Appender(Log4j2Watcher watcher, ThresholdFilter filter, Level threshold) {
super(LOG4J2_WATCHER_APPENDER, filter, null);
this.watcher = watcher;
this.filter = filter;
this.threshold = threshold;
}
public void append(LogEvent logEvent) {
watcher.add(logEvent, logEvent.getTimeMillis());
}
public Level getThreshold() {
return threshold;
}
public void setThreshold(Level threshold) {
this.threshold = threshold;
removeFilter(filter);
filter = ThresholdFilter.createFilter(threshold, Filter.Result.ACCEPT, Filter.Result.DENY);
addFilter(filter);
}
}
protected class Log4j2Info extends LoggerInfo {
final Level level;
Log4j2Info(String name, Level level) {
super(name);
this.level = level;
}
@Override
public String getLevel() {
return (level != null) ? level.toString() : null;
}
@Override
public String getName() {
return name;
}
@Override
public boolean isSet() {
return (level != null) ? true : false;
}
}
public static final Logger log = LogManager.getLogger(Log4j2Watcher.class);
protected Log4j2Appender appender = null;
@Override
public String getName() {
return "Log4j2";
}
@Override
public List<String> getAllLevels() {
return Arrays.asList(
Level.ALL.toString(),
Level.TRACE.toString(),
Level.DEBUG.toString(),
Level.INFO.toString(),
Level.WARN.toString(),
Level.ERROR.toString(),
Level.FATAL.toString(),
Level.OFF.toString());
}
@Override
public void setLogLevel(String loggerName, String level) {
assert loggerName != null;
assert level != null;
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
Configuration config = ctx.getConfiguration();
LoggerConfig loggerConfig = getLoggerConfig(ctx, loggerName);
assert loggerConfig != null;
boolean madeChanges = false;
if (loggerName.equals(loggerConfig.getName()) || isRootLogger(loggerName)) {
if (level == null || "unset".equals(level) || "null".equals(level)) {
level = Level.OFF.toString();
loggerConfig.setLevel(Level.OFF);
madeChanges = true;
} else {
try {
loggerConfig.setLevel(Level.valueOf(level));
madeChanges = true;
} catch (IllegalArgumentException iae) {
log.error("{} is not a valid log level! Valid values are: {}", level, getAllLevels());
}
}
} else {
//It doesn't have it's own logger yet so let's create one
LoggerConfig explicitConfig = new LoggerConfig(loggerName, Level.valueOf(level), true);
explicitConfig.setParent(loggerConfig);
config.addLogger(loggerName, explicitConfig);
madeChanges = true;
}
if (madeChanges) {
ctx.updateLoggers();
if (log.isInfoEnabled()) {
log.info("Setting log level to '{}' for logger: {}", level, loggerName);
}
}
}
protected boolean isRootLogger(String loggerName) {
return LoggerInfo.ROOT_NAME.equals(loggerName);
}
protected LoggerConfig getLoggerConfig(LoggerContext ctx, String loggerName) {
Configuration config = ctx.getConfiguration();
return isRootLogger(loggerName) ? config.getLoggerConfig(LogManager.ROOT_LOGGER_NAME)
: config.getLoggerConfig(loggerName);
}
@Override
public Collection<LoggerInfo> getAllLoggers() {
Logger root = LogManager.getRootLogger();
LoggerContext ctx = (LoggerContext)LogManager.getContext(false);
Map<String,LoggerInfo> map = new HashMap<>(ctx.getLoggers().size());
//First let's get the explicitly configured loggers
Map<String, LoggerConfig> loggers = ctx.getConfiguration().getLoggers();
for(Map.Entry<String, LoggerConfig> logger : loggers.entrySet()) {
String name = logger.getKey();
if (logger == root || root.equals(logger) || isRootLogger(name) || "".equals(name)) {
continue;
}
map.put(name, new Log4j2Info(name, logger.getValue().getLevel()));
}
for (org.apache.logging.log4j.core.Logger logger : ctx.getLoggers()) {
String name = logger.getName();
if (logger == root || root.equals(logger) || isRootLogger(name))
continue;
map.put(name, new Log4j2Info(name, logger.getLevel()));
while (true) {
int dot = name.lastIndexOf(".");
if (dot < 0)
break;
name = name.substring(0, dot);
if (!map.containsKey(name))
map.put(name, new Log4j2Info(name, null));
}
}
map.put(LoggerInfo.ROOT_NAME, new Log4j2Info(LoggerInfo.ROOT_NAME, root.getLevel()));
return map.values();
}
@Override
public void setThreshold(String level) {
Log4j2Appender app = getAppender();
Level current = app.getThreshold();
app.setThreshold(Level.toLevel(level));
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
LoggerConfig config = getLoggerConfig(ctx, LoggerInfo.ROOT_NAME);
config.removeAppender(app.getName());
config.addAppender(app, app.getThreshold(), app.getFilter());
((LoggerContext)LogManager.getContext(false)).updateLoggers();
if (log.isInfoEnabled()) {
log.info("Updated watcher threshold from {} to {} ", current, level);
}
}
@Override
public String getThreshold() {
return String.valueOf(getAppender().getThreshold());
}
protected Log4j2Appender getAppender() {
if (appender == null)
throw new IllegalStateException("No appenders configured! Must call registerListener(ListenerConfig) first.");
return appender;
}
@Override
public void registerListener(ListenerConfig cfg) {
if (history != null)
throw new IllegalStateException("History already registered");
history = new CircularList<LogEvent>(cfg.size);
Level threshold = (cfg.threshold != null) ? Level.toLevel(cfg.threshold) : Level.WARN;
ThresholdFilter filter = ThresholdFilter.createFilter(threshold, Filter.Result.ACCEPT, Filter.Result.DENY);
// If there's already an appender like this, remove it
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
LoggerConfig config = getLoggerConfig(ctx, LoggerInfo.ROOT_NAME);
appender = new Log4j2Appender(this, filter, threshold); // "Log4j2WatcherAppender"
config.removeAppender(appender.getName());
if (!appender.isStarted())
appender.start();
config.addAppender(appender, threshold, filter);
ctx.updateLoggers();
}
@Override
public long getTimestamp(LogEvent event) {
return event.getTimeMillis();
}
@Override
public SolrDocument toSolrDocument(LogEvent event) {
SolrDocument doc = new SolrDocument();
doc.setField("time", new Date(event.getTimeMillis()));
doc.setField("level", event.getLevel().toString());
doc.setField("logger", event.getLoggerName());
Message message = event.getMessage();
doc.setField("message", message.getFormattedMessage());
Throwable t = message.getThrowable();
if (t != null)
doc.setField("trace", Throwables.getStackTraceAsString(t));
Map<String,String> contextMap = event.getContextMap();
if (contextMap != null) {
for (String key : contextMap.keySet())
doc.setField(key, contextMap.get(key));
}
if (!doc.containsKey("core"))
doc.setField("core", ""); // avoids an ugly "undefined" column in the UI
return doc;
}
}

View File

@ -14,10 +14,9 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* Log4j based implementation of {@link org.apache.solr.logging.LogWatcher}
/**
* LOG4J2 based implementation of {@link org.apache.solr.logging.LogWatcher}
*/
package org.apache.solr.logging.log4j;
package org.apache.solr.logging.log4j2;

View File

@ -153,6 +153,7 @@ public class SolrDispatchFilter extends BaseSolrFilter {
SolrRequestParsers.fileCleaningTracker = new SolrFileCleaningTracker();
StartupLoggingUtils.checkLogDir();
log.info("Using logger factory {}", StartupLoggingUtils.getLoggerImplStr());
logWelcomeBanner();
String muteConsole = System.getProperty(SOLR_LOG_MUTECONSOLE);
if (muteConsole != null && !Arrays.asList("false","0","off","no").contains(muteConsole.toLowerCase(Locale.ROOT))) {

View File

@ -4317,7 +4317,7 @@ public class SolrCLI {
* ...
* solr.log -&gt; solr.log.1
* </pre>
* @param generations number of generations to keep. Should agree with setting in log4j.properties
* @param generations number of generations to keep. Should agree with setting in log4j2.xml
* @return 0 if success
* @throws Exception if problems
*/

View File

@ -16,15 +16,18 @@
*/
package org.apache.solr.util;
import java.nio.charset.Charset;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.WeakHashMap;
import org.apache.log4j.Layout;
import org.apache.log4j.Level;
import org.apache.log4j.spi.LoggingEvent;
import org.apache.log4j.spi.ThrowableInformation;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.core.LogEvent;
import org.apache.logging.log4j.core.config.plugins.Plugin;
import org.apache.logging.log4j.core.config.plugins.PluginAttribute;
import org.apache.logging.log4j.core.config.plugins.PluginFactory;
import org.apache.logging.log4j.core.layout.AbstractStringLayout;
import org.apache.solr.cloud.ZkController;
import org.apache.solr.common.SolrException;
import org.apache.solr.common.StringUtils;
@ -43,7 +46,18 @@ import static org.apache.solr.common.cloud.ZkStateReader.REPLICA_PROP;
import static org.apache.solr.common.cloud.ZkStateReader.SHARD_ID_PROP;
@SuppressForbidden(reason = "class is specific to log4j")
public class SolrLogLayout extends Layout {
@Plugin(name = "SolrLogLayout", category = "Core", elementType = "layout", printObject = true)
public class SolrLogLayout extends AbstractStringLayout {
protected SolrLogLayout(Charset charset) {
super(charset);
}
@PluginFactory
public static SolrLogLayout createLayout(@PluginAttribute(value = "charset", defaultString = "UTF-8") Charset charset) {
return new SolrLogLayout(charset);
}
/**
* Add this interface to a thread group and the string returned by getTag()
* will appear in log statements of any threads under that group.
@ -98,7 +112,7 @@ public class SolrLogLayout extends Layout {
public Map<String,String> classAliases = new HashMap<>();
public void appendThread(StringBuilder sb, LoggingEvent event) {
public void appendThread(StringBuilder sb, LogEvent event) {
Thread th = Thread.currentThread();
/******
@ -119,23 +133,23 @@ public class SolrLogLayout extends Layout {
}
@Override
public String format(LoggingEvent event) {
public String toSerializable(LogEvent event) {
return _format(event);
}
public String _format(LoggingEvent event) {
String message = (String) event.getMessage();
public String _format(LogEvent event) {
String message = event.getMessage().getFormattedMessage();
if (message == null) {
message = "";
}
StringBuilder sb = new StringBuilder(message.length() + 80);
long now = event.timeStamp;
long now = event.getTimeMillis();
long timeFromStart = now - startTime;
long timeSinceLast = now - lastTime;
lastTime = now;
String shortClassName = getShortClassName(event.getLocationInformation().getClassName(),
event.getLocationInformation().getMethodName());
String shortClassName = getShortClassName(event.getSource().getClassName(),
event.getSource().getMethodName());
/***
* sb.append(timeFromStart).append(' ').append(timeSinceLast);
@ -212,21 +226,20 @@ public class SolrLogLayout extends Layout {
sb.append(' ');
appendMultiLineString(sb, message);
ThrowableInformation thInfo = event.getThrowableInformation();
if (thInfo != null) {
Throwable th = event.getThrowableInformation().getThrowable();
if (th != null) {
sb.append(' ');
String err = SolrException.toStr(th);
String ignoredMsg = SolrException.doIgnore(th, err);
if (ignoredMsg != null) {
sb.append(ignoredMsg);
} else {
sb.append(err);
}
Throwable th = event.getThrown();
if (th != null) {
sb.append(' ');
String err = SolrException.toStr(th);
String ignoredMsg = SolrException.doIgnore(th, err);
if (ignoredMsg != null) {
sb.append(ignoredMsg);
} else {
sb.append(err);
}
}
sb.append('\n');
/***
@ -363,14 +376,6 @@ public class SolrLogLayout extends Layout {
return sb.toString() + '.' + method;
}
@Override
public void activateOptions() {}
@Override
public boolean ignoresThrowable() {
return false;
}
private void appendMDC(StringBuilder sb) {
if (!StringUtils.isEmpty(MDC.get(NODE_NAME_PROP))) {

View File

@ -18,12 +18,15 @@
package org.apache.solr.util;
import java.lang.invoke.MethodHandles;
import java.util.Enumeration;
import java.util.Map;
import org.apache.log4j.Appender;
import org.apache.log4j.ConsoleAppender;
import org.apache.log4j.Level;
import org.apache.log4j.LogManager;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.ConsoleAppender;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.solr.common.util.SuppressForbidden;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@ -49,6 +52,10 @@ public final class StartupLoggingUtils {
}
}
public static String getLoggerImplStr() {
return binder.getLoggerFactoryClassStr();
}
/**
* Disables all log4j ConsoleAppender's by modifying log4j configuration dynamically.
* Must only be used during early startup
@ -61,15 +68,16 @@ public final class StartupLoggingUtils {
logNotSupported("Could not mute logging to console.");
return false;
}
org.apache.log4j.Logger rootLogger = LogManager.getRootLogger();
Enumeration appenders = rootLogger.getAllAppenders();
while (appenders.hasMoreElements()) {
Appender appender = (Appender) appenders.nextElement();
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
Configuration config = ctx.getConfiguration();
LoggerConfig loggerConfig = config.getLoggerConfig(LogManager.ROOT_LOGGER_NAME);
Map<String, Appender> appenders = loggerConfig.getAppenders();
appenders.forEach((name, appender) -> {
if (appender instanceof ConsoleAppender) {
log.info("Property solr.log.muteconsole given. Muting ConsoleAppender named " + appender.getName());
rootLogger.removeAppender(appender);
loggerConfig.removeAppender(name);
ctx.updateLoggers();
}
}
});
return true;
} catch (Exception e) {
logNotSupported("Could not mute logging to console.");
@ -89,7 +97,12 @@ public final class StartupLoggingUtils {
logNotSupported("Could not change log level.");
return false;
}
LogManager.getRootLogger().setLevel(Level.toLevel(logLevel, Level.INFO));
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
Configuration config = ctx.getConfiguration();
LoggerConfig loggerConfig = config.getRootLogger();
loggerConfig.setLevel(Level.toLevel(logLevel, Level.INFO));
ctx.updateLoggers();
return true;
} catch (Exception e) {
logNotSupported("Could not change log level.");

View File

@ -1,38 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
log4j.logger.org.apache.directory=WARN
log4j.logger.org.apache.solr.hadoop=INFO
#log4j.logger.org.apache.solr.update.processor.LogUpdateProcessorFactory=DEBUG
#log4j.logger.org.apache.solr.update.processor.DistributedUpdateProcessor=DEBUG
#log4j.logger.org.apache.solr.update.PeerSync=DEBUG
#log4j.logger.org.apache.solr.core.CoreContainer=DEBUG
#log4j.logger.org.apache.solr.cloud.RecoveryStrategy=DEBUG
#log4j.logger.org.apache.solr.cloud.SyncStrategy=DEBUG
#log4j.logger.org.apache.solr.handler.admin.CoreAdminHandler=DEBUG
#log4j.logger.org.apache.solr.cloud.ZkController=DEBUG
#log4j.logger.org.apache.solr.update.DefaultSolrCoreState=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ConnectionManager=DEBUG
#log4j.logger.org.apache.solr.update.UpdateLog=DEBUG
#log4j.logger.org.apache.solr.cloud.ChaosMonkey=DEBUG
#log4j.logger.org.apache.solr.update.TransactionLog=DEBUG
#log4j.logger.org.apache.solr.handler.ReplicationHandler=DEBUG
#log4j.logger.org.apache.solr.handler.IndexFetcher=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ClusterStateUtil=DEBUG
#log4j.logger.org.apache.solr.cloud.OverseerAutoReplicaFailoverThread=DEBUG
#log4j.logger.org.apache.http.wire=DEBUG
#log4j.logger.org.apache.http.headers=DEBUG
#log4j.logger.org.apache.http.impl.conn.PoolingHttpClientConnectionManager=DEBUG
#log4j.logger.org.apache.http.impl.conn.BasicClientConnectionManager=DEBUG
#log4j.logger.org.apache.http=DEBUG
#log4j.logger.org.apache.solr.client.solrj.impl.SolrHttpRequestRetryHandler=DEBUG
#log4j.logger.org.eclipse.jetty=DEBUG

View File

@ -0,0 +1,39 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="org.apache.hadoop" level="WARN"/>
<Logger name="org.apache.directory" level="WARN"/>
<Logger name="org.apache.solr.hadoop" level="INFO"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -20,11 +20,14 @@ import java.io.StringWriter;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.apache.log4j.Appender;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.log4j.SimpleLayout;
import org.apache.log4j.WriterAppender;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.WriterAppender;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.logging.log4j.core.layout.PatternLayout;
import org.apache.solr.SolrTestCaseJ4;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.core.SolrCore;
@ -44,26 +47,40 @@ public class RequestLoggingTest extends SolrTestCaseJ4 {
@Before
public void setupAppender() {
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
LoggerConfig config = ctx.getConfiguration().getLoggerConfig("RequestLoggingTest");
writer = new StringWriter();
appender = new WriterAppender(new SimpleLayout(), writer);
appender = WriterAppender.createAppender(
PatternLayout
.newBuilder()
.withPattern("%-5p [%t]: %m%n")
.build(),
null, writer, "RequestLoggingTest", false, true);
appender.start();
}
@Test
public void testLogBeforeExecuteWithCoreLogger() {
Logger logger = Logger.getLogger(SolrCore.class);
Logger logger = LogManager.getLogger(SolrCore.class);
testLogBeforeExecute(logger);
}
@Test
public void testLogBeforeExecuteWithRequestLogger() {
Logger logger = Logger.getLogger("org.apache.solr.core.SolrCore.Request");
Logger logger = LogManager.getLogger("org.apache.solr.core.SolrCore.Request");
testLogBeforeExecute(logger);
}
public void testLogBeforeExecute(Logger logger) {
Level level = logger.getLevel();
logger.setLevel(Level.DEBUG);
logger.addAppender(appender);
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
LoggerConfig config = ctx.getConfiguration().getLoggerConfig(logger.getName());
config.setLevel(Level.DEBUG);
config.addAppender(appender, Level.DEBUG, null);
ctx.updateLoggers();
try {
assertQ(req("q", "*:*"));
@ -77,8 +94,9 @@ public class RequestLoggingTest extends SolrTestCaseJ4 {
assertFalse(msg, group.contains("status"));
assertFalse(msg, group.contains("QTime"));
} finally {
logger.setLevel(level);
logger.removeAppender(appender);
config.setLevel(level);
config.removeAppender(appender.getName());
ctx.updateLoggers();
}
}
}

View File

@ -16,12 +16,16 @@
*/
package org.apache.solr.handler.admin;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.solr.SolrTestCaseJ4;
import org.apache.solr.common.params.CommonParams;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.logging.log4j.Log4jInfo;
import org.junit.BeforeClass;
import org.junit.Test;
@ -42,21 +46,29 @@ public class LoggingHandlerTest extends SolrTestCaseJ4 {
@Test
public void testLogLevelHandlerOutput() throws Exception {
Logger tst = Logger.getLogger("org.apache.solr.SolrTestCaseJ4");
tst.setLevel(Level.INFO);
Log4jInfo wrap = new Log4jInfo(tst.getName(), tst);
Logger tst = LogManager.getLogger("org.apache.solr.SolrTestCaseJ4");
LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
LoggerConfig loggerConfig = ctx.getConfiguration().getLoggerConfig(tst.getName());
loggerConfig.setLevel(Level.INFO);
ctx.updateLoggers();
assertQ("Show Log Levels OK",
req(CommonParams.QT,"/admin/logging")
,"//arr[@name='loggers']/lst/str[.='"+wrap.getName()+"']/../str[@name='level'][.='"+wrap.getLevel()+"']"
,"//arr[@name='loggers']/lst/str[.='"+tst.getName()+"']/../str[@name='level'][.='"+tst.getLevel()+"']"
,"//arr[@name='loggers']/lst/str[.='org.apache']/../null[@name='level']"
);
assertQ("Set and remove a level",
assertQ("Set a level",
req(CommonParams.QT,"/admin/logging",
"set", "org.xxx.yyy.abc:null",
"set", "org.xxx.yyy.zzz:TRACE")
,"//arr[@name='loggers']/lst/str[.='org.xxx.yyy.zzz']/../str[@name='level'][.='TRACE']"
"set", tst.getName()+":TRACE")
,"//arr[@name='loggers']/lst/str[.='"+tst.getName()+"']/../str[@name='level'][.='TRACE']"
);
assertQ("Remove a level",
req(CommonParams.QT,"/admin/logging",
"set", tst.getName()+":null")
,"//arr[@name='loggers']/lst/str[.='"+tst.getName()+"']/../str[@name='level'][.='OFF']"
);
}
}

View File

@ -56,4 +56,25 @@ public class TestLogWatcher {
assertEquals(event.get("message"), "This is a test message");
}
// This seems weird to do the same thing twice, this is valid. We need to test whether listeners are replaced....
@Test
public void testLog4jWatcherRepeat() {
LogWatcher watcher = LogWatcher.newRegisteredLogWatcher(config, null);
assertEquals(watcher.getLastEvent(), -1);
log.warn("This is a test message");
assertTrue(watcher.getLastEvent() > -1);
SolrDocumentList events = watcher.getHistory(-1, new AtomicBoolean());
assertEquals(events.size(), 1);
SolrDocument event = events.get(0);
assertEquals(event.get("logger"), "org.apache.solr.logging.TestLogWatcher");
assertEquals(event.get("message"), "This is a test message");
}
}

View File

@ -47,9 +47,6 @@ public class SolrSlf4jReporterTest extends SolrTestCaseJ4 {
@Test
public void testReporter() throws Exception {
ensureLoggingConfiguredAppropriately();
LogWatcherConfig watcherCfg = new LogWatcherConfig(true, null, null, 100);
LogWatcher watcher = LogWatcher.newRegisteredLogWatcher(watcherCfg, null);
watcher.setThreshold("INFO");
Path home = Paths.get(TEST_HOME());
// define these properties, they are used in solrconfig.xml
System.setProperty("solr.test.sys.prop1", "propone");
@ -70,6 +67,10 @@ public class SolrSlf4jReporterTest extends SolrTestCaseJ4 {
assertNotNull(reporter2);
assertTrue(reporter2 instanceof SolrSlf4jReporter);
LogWatcherConfig watcherCfg = new LogWatcherConfig(true, null, null, 100);
LogWatcher watcher = LogWatcher.newRegisteredLogWatcher(watcherCfg, null);
watcher.setThreshold("INFO");
watcher.reset();
int cnt = 20;
boolean active;

View File

@ -125,6 +125,8 @@ public class TestSolrCLIRunExample extends SolrTestCaseJ4 {
JettyConfig.builder().setContext("/solr").setPort(port).build();
try {
if (solrCloudCluster == null) {
Path logDir = createTempDir("solr_logs");
System.setProperty("solr.log.dir", logDir.toString());
System.setProperty("host", "localhost");
System.setProperty("jetty.port", String.valueOf(port));
solrCloudCluster =
@ -222,6 +224,7 @@ public class TestSolrCLIRunExample extends SolrTestCaseJ4 {
System.setProperty("host", "localhost");
System.setProperty("jetty.port", String.valueOf(port));
System.setProperty("solr.log.dir", createTempDir("solr_logs").toString());
standaloneSolr = new JettySolrRunner(solrHomeDir.getAbsolutePath(), "/solr", port);
Thread bg = new Thread() {

View File

@ -72,7 +72,7 @@ solrconfig.xml.
By default, Jetty & Solr will log to the console and logs/solr.log. This can
be convenient when first getting started, but eventually you will want to
log just to a file. To configure logging, edit the log4j.properties file in
log just to a file. To configure logging, edit the log4j2.xml file in
"resources".
It is also possible to setup log4j or other popular logging frameworks.

View File

@ -240,7 +240,7 @@
Setting the value to true will instruct the underlying Lucene
IndexWriter to write its info stream to solr's log. By default,
this is enabled here, and controlled through log4j.properties.
this is enabled here, and controlled through log4j2.xml
-->
<infoStream>true</infoStream>
</indexConfig>

View File

@ -243,7 +243,7 @@
Setting the value to true will instruct the underlying Lucene
IndexWriter to write its info stream to solr's log. By default,
this is enabled here, and controlled through log4j.properties.
this is enabled here, and controlled through log4j2.xml
-->
<infoStream>true</infoStream>
</indexConfig>

View File

@ -240,7 +240,7 @@
Setting the value to true will instruct the underlying Lucene
IndexWriter to write its info stream to solr's log. By default,
this is enabled here, and controlled through log4j.properties.
this is enabled here, and controlled through log4j2.xml
-->
<infoStream>true</infoStream>
</indexConfig>

View File

@ -1,24 +0,0 @@
# Logging level
solr.log=${solr.solr.home}/../logs
log4j.rootLogger=INFO, file
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-4r [%t] %-5p %c %x [%X{collection} %X{shard} %X{replica} %X{core}] \u2013 %m%n
#- size rotation with log cleanup.
log4j.appender.file=org.apache.log4j.RollingFileAppender
log4j.appender.file.MaxFileSize=32MB
log4j.appender.file.MaxBackupIndex=10
#- File to log to and log format
log4j.appender.file.File=${solr.log}/solr.log
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; [%X{collection} %X{shard} %X{replica} %X{core}] %C; %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
# set to INFO to enable infostream log messages
log4j.logger.org.apache.solr.update.LoggingInfoStream=OFF

View File

@ -0,0 +1,53 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDOUT" target="SYSTEM_OUT">
<PatternLayout>
<Pattern>
%-4r [%t] %-5p %c %x [%X{collection} %X{shard} %X{replica} %X{core}] %c; %m%n
</Pattern>
</PatternLayout>
</Console>
<RollingFile
name="RollingFile"
fileName="${sys:solr.solr.home}/../logs/solr.log"
filePattern="${sys:solr.solr.home}/../logs/solr.%i.log.gz" >
<PatternLayout>
<Pattern>
%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; [%X{collection} %X{shard} %X{replica} %X{core}] %c; %m%n
</Pattern>
</PatternLayout>
<Policies>
<OnStartupTriggeringPolicy />
<SizeBasedTriggeringPolicy size="4 MB"/>
</Policies>
</RollingFile>
</Appenders>
<Loggers>
<Logger name="org.apache.hadoop" level="warn"/>
<Logger name="org.apache.solr.update.LoggingInfoStream" level="off"/>
<Logger name="org.apache.zookeeper" level="warn"/>
<Root level="info">
<AppenderRef ref="RollingFile"/>
<AppenderRef ref="STDOUT"/>
</Root>
</Loggers>
</Configuration>

View File

@ -0,0 +1 @@
507e22993e3a78a3ba453e76a9756a294752648d

View File

@ -0,0 +1,201 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

View File

@ -0,0 +1 @@
5e488f2c717964162016cd5138e2b1ea4dcc379f

View File

@ -1 +0,0 @@
5af35056b4d257e4b64b9e8069c0746e8b08629f

View File

@ -0,0 +1 @@
bede79a3f150711634a3047985517431bf6499f2

View File

@ -0,0 +1,201 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

@ -0,0 +1,17 @@
Apache Log4j
Copyright 1999-2017 Apache Software Foundation
This product includes software developed at
The Apache Software Foundation (http://www.apache.org/).
ResolverUtil.java
Copyright 2005-2006 Tim Fennell
Dumbster SMTP test server
Copyright 2004 Jason Paul Kitchen
TypeUtil.java
Copyright 2002-2012 Ramnivas Laddad, Juergen Hoeller, Chris Beams
picocli (http://picocli.info)
Copyright 2017 Remko Popma

View File

@ -0,0 +1 @@
e6b751e02120c08702d98750f6a80bc25343b7f5

View File

@ -0,0 +1,201 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

@ -0,0 +1,17 @@
Apache Log4j
Copyright 1999-2017 Apache Software Foundation
This product includes software developed at
The Apache Software Foundation (http://www.apache.org/).
ResolverUtil.java
Copyright 2005-2006 Tim Fennell
Dumbster SMTP test server
Copyright 2004 Jason Paul Kitchen
TypeUtil.java
Copyright 2002-2012 Ramnivas Laddad, Juergen Hoeller, Chris Beams
picocli (http://picocli.info)
Copyright 2017 Remko Popma

View File

@ -0,0 +1,201 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

@ -0,0 +1,17 @@
Apache Log4j
Copyright 1999-2017 Apache Software Foundation
This product includes software developed at
The Apache Software Foundation (http://www.apache.org/).
ResolverUtil.java
Copyright 2005-2006 Tim Fennell
Dumbster SMTP test server
Copyright 2004 Jason Paul Kitchen
TypeUtil.java
Copyright 2002-2012 Ramnivas Laddad, Juergen Hoeller, Chris Beams
picocli (http://picocli.info)
Copyright 2017 Remko Popma

View File

@ -0,0 +1 @@
9ba207b78e470fe7765ebee14f1f0336c9cbcc18

View File

@ -1 +0,0 @@
309d7b29b14573c05d4c69cc7e44da0cb17212d3

View File

@ -47,7 +47,7 @@ server/logs
server/resources
Contains configuration files, such as the Log4j configuration (log4j.properties) for configuring Solr loggers.
Contains configuration files, such as the Log4j configuration (log4j2.xml) for configuring Solr loggers.
server/scripts/cloud-scripts
@ -102,7 +102,7 @@ solrconfig.xml.
By default, Jetty & Solr will log to the console and logs/solr.log. This can
be convenient when first getting started, but eventually you will want to
log just to a file. To configure logging, edit the log4j.properties file in
log just to a file. To configure logging, edit the log4j2.xml file in
"resources".
It is also possible to setup log4j or other popular logging frameworks.

View File

@ -27,11 +27,14 @@
</configurations>
<dependencies>
<dependency org="log4j" name="log4j" rev="${/log4j/log4j}" conf="logging"/>
<dependency org="org.apache.logging.log4j" name="log4j-api" rev="${/org.apache.logging.log4j/log4j-api}" conf="logging"/>
<dependency org="org.apache.logging.log4j" name="log4j-core" rev="${/org.apache.logging.log4j/log4j-core}" conf="logging"/>
<dependency org="org.apache.logging.log4j" name="log4j-slf4j-impl" rev="${/org.apache.logging.log4j/log4j-slf4j-impl}" conf="logging"/>
<dependency org="org.apache.logging.log4j" name="log4j-1.2-api" rev="${/org.apache.logging.log4j/log4j-1.2-api}" conf="logging"/>
<dependency org="com.lmax" name="disruptor" rev="${/com.lmax/disruptor}" conf="logging"/>
<dependency org="org.slf4j" name="slf4j-api" rev="${/org.slf4j/slf4j-api}" conf="logging"/>
<dependency org="org.slf4j" name="jcl-over-slf4j" rev="${/org.slf4j/jcl-over-slf4j}" conf="logging"/>
<dependency org="org.slf4j" name="jul-to-slf4j" rev="${/org.slf4j/jul-to-slf4j}" conf="logging"/>
<dependency org="org.slf4j" name="slf4j-log4j12" rev="${/org.slf4j/slf4j-log4j12}" conf="logging"/>
<dependency org="org.slf4j" name="jul-to-slf4j" rev="${/org.slf4j/jul-to-slf4j}" conf="logging"/>
<dependency org="io.dropwizard.metrics" name="metrics-core" rev="${/io.dropwizard.metrics/metrics-core}" conf="metrics" />
<dependency org="io.dropwizard.metrics" name="metrics-jetty9" rev="${/io.dropwizard.metrics/metrics-jetty9}" conf="metrics" />

View File

@ -1,29 +0,0 @@
# Default Solr log4j config
# rootLogger log level may be programmatically overridden by -Dsolr.log.level
solr.log=${solr.log.dir}
log4j.rootLogger=INFO, file, CONSOLE
# Console appender will be programmatically disabled when Solr is started with option -Dsolr.log.muteconsole
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss.SSS} %-5p (%t) [%X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
#- size rotation with log cleanup.
log4j.appender.file=org.apache.log4j.RollingFileAppender
log4j.appender.file.MaxFileSize=32MB
log4j.appender.file.MaxBackupIndex=10
#- File to log to and log format
log4j.appender.file.File=${solr.log}/solr.log
log4j.appender.file.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.file.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss.SSS} %-5p (%t) [%X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
# Adjust logging levels that should differ from root logger
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
log4j.logger.org.eclipse.jetty=WARN
log4j.logger.org.eclipse.jetty.server.Server=INFO
log4j.logger.org.eclipse.jetty.server.ServerConnector=INFO
# set to INFO to enable infostream log messages
log4j.logger.org.apache.solr.update.LoggingInfoStream=OFF

View File

@ -0,0 +1,53 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDOUT" target="SYSTEM_OUT">
<PatternLayout>
<Pattern>
%d{yyyy-MM-dd HH:mm:ss.SSS} %-5p (%t) [%X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
</Console>
<RollingFile
name="RollingFile"
fileName="${sys:solr.solr.home}/../logs/solr.log"
filePattern="${sys:solr.solr.home}/../logs/solr.%i.log.gz" >
<PatternLayout>
<Pattern>
%d{yyyy-MM-dd HH:mm:ss.SSS} %-5p (%t) [%X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
<Policies>
<OnStartupTriggeringPolicy />
<SizeBasedTriggeringPolicy size="4 MB"/>
</Policies>
</RollingFile>
</Appenders>
<Loggers>
<Logger name="org.apache.hadoop" level="warn"/>
<Logger name="org.apache.solr.update.LoggingInfoStream" level="off"/>
<Logger name="org.apache.zookeeper" level="warn"/>
<Root level="info">
<AppenderRef ref="RollingFile"/>
<AppenderRef ref="STDOUT"/>
</Root>
</Loggers>
</Configuration>

View File

@ -1,12 +0,0 @@
# Logging level
log4j.rootLogger=INFO, stderr
# log to stderr
log4j.appender.stderr = org.apache.log4j.ConsoleAppender
log4j.appender.stderr.Target = System.err
log4j.appender.stderr.layout = org.apache.log4j.PatternLayout
log4j.appender.stderr.layout.ConversionPattern=%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %C; %m%n
# quiet down the ZK logging for cli tools
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.solr.common.cloud=WARN

View File

@ -0,0 +1,37 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-5p - %d{yyyy-MM-dd HH:mm:ss.SSS}; %c; %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="log4j.logger.org.apache.solr.common.cloud" level="WARN"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -8,9 +8,9 @@ run_solr_snapshot_tool() {
if [ -n "$LOG4J_PROPS" ]; then
log4j_config="file:${LOG4J_PROPS}"
else
log4j_config="file:${scriptDir}/log4j.properties"
log4j_config="file:${scriptDir}/log4j2.xml"
fi
PATH=${JAVA_HOME}/bin:${PATH} ${JVM} ${ZKCLI_JVM_FLAGS} -Dlog4j.configuration=${log4j_config} \
PATH=${JAVA_HOME}/bin:${PATH} ${JVM} ${ZKCLI_JVM_FLAGS} -Dlog4j.configurationFile=${log4j_config} \
-classpath "${solrLibPath}" org.apache.solr.core.snapshots.SolrSnapshotsTool "$@" 2> /dev/null
}

View File

@ -12,7 +12,7 @@ if "%SDIR:~-1%"=="\" set SDIR=%SDIR:~0,-1%
if defined LOG4J_PROPS (
set "LOG4J_CONFIG=file:%LOG4J_PROPS%"
) else (
set "LOG4J_CONFIG=file:%SDIR%\log4j.properties"
set "LOG4J_CONFIG=file:%SDIR%\log4j2.xml"
)
REM Settings for ZK ACL
@ -21,5 +21,5 @@ REM -DzkCredentialsProvider=org.apache.solr.common.cloud.VMParamsSingleSetCrede
REM -DzkDigestUsername=admin-user -DzkDigestPassword=CHANGEME-ADMIN-PASSWORD ^
REM -DzkDigestReadonlyUsername=readonly-user -DzkDigestReadonlyPassword=CHANGEME-READONLY-PASSWORD
"%JVM%" %SOLR_ZK_CREDS_AND_ACLS% %ZKCLI_JVM_FLAGS% -Dlog4j.configuration="%LOG4J_CONFIG%" ^
"%JVM%" %SOLR_ZK_CREDS_AND_ACLS% %ZKCLI_JVM_FLAGS% -Dlog4j.configurationFile="%LOG4J_CONFIG%" ^
-classpath "%SDIR%\..\..\solr-webapp\webapp\WEB-INF\lib\*;%SDIR%\..\..\lib\ext\*;%SDIR%\..\..\lib\*" org.apache.solr.cloud.ZkCLI %*

View File

@ -12,7 +12,7 @@ sdir="`dirname \"$0\"`"
if [ -n "$LOG4J_PROPS" ]; then
log4j_config="file:$LOG4J_PROPS"
else
log4j_config="file:$sdir/log4j.properties"
log4j_config="file:$sdir/log4j2.xml"
fi
# Settings for ZK ACL
@ -21,6 +21,6 @@ fi
# -DzkDigestUsername=admin-user -DzkDigestPassword=CHANGEME-ADMIN-PASSWORD \
# -DzkDigestReadonlyUsername=readonly-user -DzkDigestReadonlyPassword=CHANGEME-READONLY-PASSWORD"
PATH=$JAVA_HOME/bin:$PATH $JVM $SOLR_ZK_CREDS_AND_ACLS $ZKCLI_JVM_FLAGS -Dlog4j.configuration=$log4j_config \
PATH=$JAVA_HOME/bin:$PATH $JVM $SOLR_ZK_CREDS_AND_ACLS $ZKCLI_JVM_FLAGS -Dlog4j.configurationFile=$log4j_config \
-classpath "$sdir/../../solr-webapp/webapp/WEB-INF/lib/*:$sdir/../../lib/ext/*:$sdir/../../lib/*" org.apache.solr.cloud.ZkCLI ${1+"$@"}

View File

@ -247,7 +247,7 @@
Setting the value to true will instruct the underlying Lucene
IndexWriter to write its info stream to solr's log. By default,
this is enabled here, and controlled through log4j.properties.
this is enabled here, and controlled through log4j2.xml
-->
<infoStream>true</infoStream>
</indexConfig>

View File

@ -29,6 +29,8 @@
<dependency org="org.slf4j" name="jcl-over-slf4j" rev="${/org.slf4j/jcl-over-slf4j}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-api" rev="${/org.slf4j/slf4j-api}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-simple" rev="${/org.slf4j/slf4j-simple}" conf="compile"/>
<dependency org="log4j" name="log4j" rev="${/log4j/log4j}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-api" rev="${/org.apache.logging.log4j/log4j-api}" conf="compile"/>
<dependency org="org.apache.logging.log4j" name="log4j-core" rev="${/org.apache.logging.log4j/log4j-core}" conf="compile"/>
</dependencies>
</ivy-module>

View File

@ -86,11 +86,11 @@ bin/solr start -f -q
Solr uses http://logging.apache.org/log4j/{ivy-log4j-version}/[Log4J version {ivy-log4j-version}] for logging which is configured using `server/resources/log4j.properties`. Take a moment to inspect the contents of the `log4j.properties` file so that you are familiar with its structure. By default, Solr log messages will be written to `SOLR_LOGS_DIR/solr.log`.
When you're ready to deploy Solr in production, set the variable `SOLR_LOGS_DIR` to the location where you want Solr to write log files, such as `/var/solr/logs`. You may also want to tweak `log4j.properties`. Note that if you installed Solr as a service using the instructions provided in <<taking-solr-to-production.adoc#taking-solr-to-production,Taking Solr to Production>>, then see `/var/solr/log4j.properties` instead of the default `server/resources` version.
When you're ready to deploy Solr in production, set the variable `SOLR_LOGS_DIR` to the location where you want Solr to write log files, such as `/var/solr/logs`. You may also want to tweak `log4j2.xml`. Note that if you installed Solr as a service using the instructions provided in <<taking-solr-to-production.adoc#taking-solr-to-production,Taking Solr to Production>>, then see `/var/solr/log4j2.xml` instead of the default `server/resources` version.
When starting Solr in the foreground (`-f` option), all logs will be sent to the console, in addition to `solr.log`. When starting Solr in the background, it will write all `stdout` and `stderr` output to a log file in `solr-<port>-console.log`, and automatically disable the CONSOLE logger configured in `log4j.properties`, having the same effect as if you removed the CONSOLE appender from the rootLogger manually.
When starting Solr in the foreground (`-f` option), all logs will be sent to the console, in addition to `solr.log`. When starting Solr in the background, it will write all `stdout` and `stderr` output to a log file in `solr-<port>-console.log`, and automatically disable the CONSOLE logger configured in `log4j2.xml`, having the same effect as if you removed the CONSOLE appender from the rootLogger manually.
Also, in `log4j.properties` if the default log rotation size threshold of 32MB is too small for production servers then you should increase it to a larger value (such as 100MB or more).
Also, in `log4j2.xml` if the default log rotation size threshold of 32MB is too small for production servers then you should increase it to a larger value (such as 100MB or more).
[source,text]
----
@ -99,7 +99,7 @@ log4j.appender.file.MaxFileSize=100MB
Java Garbage Collection logs are rotated by the JVM when size hits 20M, for a max of 9 generations. Old GC logs are moved to `SOLR_LOGS_DIR/archived`. These settings can only be changed by editing the start scripts.
On every startup of Solr, the start script will clean up old logs and rotate the main `solr.log` file. If you changed the `log4j.appender.file.MaxBackupIndex` setting in `log4j.properties`, you also need to change the corresponding setting `-rotate_solr_logs 10` in the start script.
On every startup of Solr, the start script will clean up old logs and rotate the main `solr.log` file. If you changed the `log4j.appender.file.MaxBackupIndex` setting in `log4j2.xml`, you also need to change the corresponding setting `-rotate_solr_logs 10` in the start script.
You can disable the automatic log rotation at startup by changing the setting `SOLR_LOG_PRESTART_ROTATION` found in `bin/solr.in.sh` or `bin/solr.in.cmd` to false.

View File

@ -122,12 +122,12 @@ This parameter is ignored when running examples (`-e`), as the `solr.solr.home`
*Example*: `bin/solr start -s newHome`
`-v`::
Be more verbose. This changes the logging level of log4j from `INFO` to `DEBUG`, having the same effect as if you edited `log4j.properties` accordingly.
Be more verbose. This changes the logging level of log4j from `INFO` to `DEBUG`, having the same effect as if you edited `log4j2.xml` accordingly.
+
*Example*: `bin/solr start -f -v`
`-q`::
Be more quiet. This changes the logging level of log4j from `INFO` to `WARN`, having the same effect as if you edited `log4j.properties` accordingly. This can be useful in a production setting where you want to limit logging to warnings and errors.
Be more quiet. This changes the logging level of log4j from `INFO` to `WARN`, having the same effect as if you edited `log4j2.xml` accordingly. This can be useful in a production setting where you want to limit logging to warnings and errors.
+
*Example*: `bin/solr start -f -q`

View File

@ -107,11 +107,11 @@ The `SOLR_PID_DIR` variable sets the directory where the <<solr-control-script-r
==== Log Settings
Solr uses Apache Log4J for logging. The installation script copies `/opt/solr/server/resources/log4j.properties` to `/var/solr/log4j.properties`. Take a moment to verify that the Solr include file is configured to send logs to the correct location by checking the following settings in `/etc/default/solr.in.sh`:
Solr uses Apache Log4J for logging. The installation script copies `/opt/solr/server/resources/log4j2.xml` to `/var/solr/log4j2.xml`. Take a moment to verify that the Solr include file is configured to send logs to the correct location by checking the following settings in `/etc/default/solr.in.sh`:
[source,bash]
----
LOG4J_PROPS=/var/solr/log4j.properties
LOG4J_PROPS=/var/solr/log4j2.xml
SOLR_LOGS_DIR=/var/solr/logs
----

View File

@ -40,7 +40,7 @@
<dependency org="org.slf4j" name="slf4j-api" rev="${/org.slf4j/slf4j-api}" conf="compile"/>
<dependency org="org.slf4j" name="jcl-over-slf4j" rev="${/org.slf4j/jcl-over-slf4j}" conf="compile"/>
<dependency org="org.slf4j" name="slf4j-log4j12" rev="${/org.slf4j/slf4j-log4j12}" conf="test"/>
<dependency org="org.apache.logging.log4j" name="log4j-slf4j-impl" rev="${/org.apache.logging.log4j/log4j-slf4j-impl}" conf="test"/>
<dependency org="org.mockito" name="mockito-core" rev="${/org.mockito/mockito-core}" conf="test"/>
<dependency org="net.bytebuddy" name="byte-buddy" rev="${/net.bytebuddy/byte-buddy}" conf="test"/>

View File

@ -1,32 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
log4j.logger.org.apache.directory=WARN
log4j.logger.org.apache.solr.hadoop=INFO
#log4j.logger.org.apache.solr.update.processor.LogUpdateProcessorFactory=DEBUG
#log4j.logger.org.apache.solr.update.processor.DistributedUpdateProcessor=DEBUG
#log4j.logger.org.apache.solr.update.PeerSync=DEBUG
#log4j.logger.org.apache.solr.core.CoreContainer=DEBUG
#log4j.logger.org.apache.solr.cloud.RecoveryStrategy=DEBUG
#log4j.logger.org.apache.solr.cloud.SyncStrategy=DEBUG
#log4j.logger.org.apache.solr.handler.admin.CoreAdminHandler=DEBUG
#log4j.logger.org.apache.solr.cloud.ZkController=DEBUG
#log4j.logger.org.apache.solr.update.DefaultSolrCoreState=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ConnectionManager=DEBUG
#log4j.logger.org.apache.solr.update.UpdateLog=DEBUG
#log4j.logger.org.apache.solr.cloud.ChaosMonkey=DEBUG
#log4j.logger.org.apache.solr.update.TransactionLog=DEBUG
#log4j.logger.org.apache.solr.handler.ReplicationHandler=DEBUG
#log4j.logger.org.apache.solr.handler.IndexFetcher=DEBUG
#log4j.logger.org.apache.solr.common.cloud.ClusterStateUtil=DEBUG
#log4j.logger.org.apache.solr.cloud.OverseerAutoReplicaFailoverThread=DEBUG
# log4j.logger.org.apache.http.impl.conn.PoolingHttpClientConnectionManager=DEBUG

View File

@ -0,0 +1,39 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="org.apache.hadoop" level="WARN"/>
<Logger name="org.apache.directory" level="WARN"/>
<Logger name="log4j.logger.org.apache.solr.hadoop" level="INFO"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -70,6 +70,7 @@ import com.carrotsearch.randomizedtesting.rules.SystemPropertiesRestoreRule;
import org.apache.commons.io.FileUtils;
import org.apache.http.client.HttpClient;
import org.apache.logging.log4j.Level;
import org.apache.lucene.analysis.MockAnalyzer;
import org.apache.lucene.analysis.MockTokenizer;
import org.apache.lucene.index.IndexWriterConfig;
@ -396,7 +397,7 @@ public abstract class SolrTestCaseJ4 extends LuceneTestCase {
return result;
}
private static Map<String, String> savedClassLogLevels = new HashMap<>();
private static Map<String, Level> savedClassLogLevels = new HashMap<>();
public static void initClassLogLevels() {
Class currentClass = RandomizedContext.current().getTargetClass();
@ -404,11 +405,11 @@ public abstract class SolrTestCaseJ4 extends LuceneTestCase {
if (annotation == null) {
return;
}
Map<String, String> previousLevels = LogLevel.Configurer.setLevels(annotation.value());
Map<String, Level> previousLevels = LogLevel.Configurer.setLevels(annotation.value());
savedClassLogLevels.putAll(previousLevels);
}
private Map<String, String> savedMethodLogLevels = new HashMap<>();
private Map<String, Level> savedMethodLogLevels = new HashMap<>();
@Before
public void initMethodLogLevels() {
@ -417,7 +418,7 @@ public abstract class SolrTestCaseJ4 extends LuceneTestCase {
if (annotation == null) {
return;
}
Map<String, String> previousLevels = LogLevel.Configurer.setLevels(annotation.value());
Map<String, Level> previousLevels = LogLevel.Configurer.setLevels(annotation.value());
savedMethodLogLevels.putAll(previousLevels);
}

View File

@ -26,8 +26,10 @@ import java.lang.annotation.Target;
import java.util.HashMap;
import java.util.Map;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.solr.common.util.SuppressForbidden;
/**
@ -57,35 +59,44 @@ public @interface LogLevel {
Map<String, Level> testlevels = new HashMap<>();
for (String levelSetting : input.split(";")) {
String[] parts = levelSetting.split("=");
testlevels.put(parts[0], Level.toLevel(parts[1]));
testlevels.put(parts[0], parseLevel(parts[1]));
}
return testlevels;
}
private static String levelAsString(Level level) {
return level == null ? null : level.toString();
}
private static Level parseLevel(String level) {
return level == null ? null : Level.toLevel(level);
}
public static void restoreLogLevels(Map<String, String> savedLogLevels) {
savedLogLevels.forEach((name, level) -> {
Logger logger = Logger.getLogger(name);
logger.setLevel(parseLevel(level));
});
public static void restoreLogLevels(Map<String, Level> savedLogLevels) {
setLogLevels(savedLogLevels);
}
public static Map<String, String> setLevels(String value) {
Map<String, String> oldLevels = new HashMap<>();
parseFrom(value).forEach((name, level) -> {
Logger logger = Logger.getLogger(name);
oldLevels.put(name, levelAsString(logger.getLevel()));
logger.setLevel(level);
public static Map<String, Level> setLevels(String value) {
return setLogLevels(parseFrom(value));
}
private static Map<String, Level> setLogLevels(Map<String, Level> logLevels) {
LoggerContext ctx = LoggerContext.getContext(false);
Configuration config = ctx.getConfiguration();
Map<String, Level> oldLevels = new HashMap<>();
logLevels.forEach((loggerName, level) -> {
LoggerConfig logConfig = config.getLoggerConfig(loggerName);
// what the initial logger level was. It will use the root value if logger is being defined for the first time
oldLevels.put(loggerName, logConfig.getLevel());
if (loggerName.equals(logConfig.getName())) {
logConfig.setLevel(level);
} else {
LoggerConfig loggerConfig = new LoggerConfig(loggerName, level, true);
loggerConfig.setLevel(level);
config.addLogger(loggerName, loggerConfig);
}
});
ctx.updateLoggers();
return oldLevels;
}
}
}

View File

@ -1,11 +0,0 @@
# Logging level
log4j.rootLogger=INFO, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.Target=System.err
log4j.appender.CONSOLE.layout=org.apache.log4j.EnhancedPatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
log4j.logger.org.apache.zookeeper=WARN
log4j.logger.org.apache.hadoop=WARN
log4j.logger.org.apache.directory=WARN
log4j.logger.org.apache.solr.hadoop=INFO

View File

@ -0,0 +1,39 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Configuration>
<Appenders>
<Console name="STDERR" target="SYSTEM_ERR">
<PatternLayout>
<Pattern>
%-4r %-5p (%t) [%X{node_name} %X{collection} %X{shard} %X{replica} %X{core}] %c{1.} %m%n
</Pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="org.apache.zookeeper" level="WARN"/>
<Logger name="org.apache.hadoop" level="WARN"/>
<Logger name="org.apache.directory" level="WARN"/>
<Logger name="log4j.logger.org.apache.solr.hadoop" level="INFO"/>
<Root level="INFO">
<AppenderRef ref="STDERR"/>
</Root>
</Loggers>
</Configuration>

View File

@ -17,8 +17,8 @@
package org.apache.solr;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.solr.common.util.SuppressForbidden;
import org.apache.solr.util.LogLevel;
import org.junit.Test;
@ -29,19 +29,15 @@ public class TestLogLevelAnnotations extends SolrTestCaseJ4 {
@Test
public void testClassLogLevels() {
Logger classLogLevel = Logger.getLogger("org.apache.solr.ClassLogLevel");
assertEquals(Level.ERROR, classLogLevel.getLevel());
Logger methodLogLevel = Logger.getLogger("org.apache.solr.MethodLogLevel");
assertEquals(Level.WARN, methodLogLevel.getLevel());
assertEquals(Level.ERROR, LogManager.getLogger("org.apache.solr.ClassLogLevel").getLevel());
assertEquals(Level.WARN, LogManager.getLogger("org.apache.solr.MethodLogLevel").getLevel());
}
@Test
@LogLevel("org.apache.solr.MethodLogLevel=debug")
public void testMethodLogLevels() {
Logger classLogLevel = Logger.getLogger("org.apache.solr.ClassLogLevel");
assertEquals(Level.ERROR, classLogLevel.getLevel());
Logger methodLogLevel = Logger.getLogger("org.apache.solr.MethodLogLevel");
assertEquals(Level.DEBUG, methodLogLevel.getLevel());
assertEquals(Level.ERROR, LogManager.getLogger("org.apache.solr.ClassLogLevel").getLevel());
assertEquals(Level.DEBUG, LogManager.getLogger("org.apache.solr.MethodLogLevel").getLevel());
}
}