Repository: logging-log4j2 Updated Branches: refs/heads/master 361785ab7 -> 2d18d39ca
[LOG4J2-1578] RoutingAppender can be configured with scripts. Don't share a Bindings object accross script invocations. Instead, create a new Bindings objects and share ConcurrentMap for the scripts static variables. Project: http://git-wip-us.apache.org/repos/asf/logging-log4j2/repo Commit: http://git-wip-us.apache.org/repos/asf/logging-log4j2/commit/2d18d39c Tree: http://git-wip-us.apache.org/repos/asf/logging-log4j2/tree/2d18d39c Diff: http://git-wip-us.apache.org/repos/asf/logging-log4j2/diff/2d18d39c Branch: refs/heads/master Commit: 2d18d39caa141cba00eca3b46931f79fb9d2186d Parents: 361785a Author: Gary Gregory <[email protected]> Authored: Wed Sep 14 18:53:15 2016 -0700 Committer: Gary Gregory <[email protected]> Committed: Wed Sep 14 18:53:15 2016 -0700 ---------------------------------------------------------------------- .../log4j/core/appender/routing/Routes.java | 23 +- .../core/appender/routing/RoutingAppender.java | 14 +- .../log4j/core/script/ScriptManager.java | 559 ++++++++++--------- .../routing/DefaultRouteScriptAppenderTest.java | 9 +- .../routing/RoutesScriptAppenderTest.java | 47 +- 5 files changed, 338 insertions(+), 314 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/2d18d39c/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/Routes.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/Routes.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/Routes.java index 0fbbdc4..bf3ccef 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/Routes.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/Routes.java @@ -16,7 +16,10 @@ */ package org.apache.logging.log4j.core.appender.routing; +import static org.apache.logging.log4j.core.appender.routing.RoutingAppender.STATIC_VARIABLES_KEY; + import java.util.Objects; +import java.util.concurrent.ConcurrentMap; import javax.script.Bindings; @@ -138,8 +141,6 @@ public final class Routes { return new Builder(); } - private Bindings bindings; - private final Configuration configuration; private final String pattern; @@ -148,7 +149,7 @@ public final class Routes { // TODO Why not make this a Map or add a Map. private final Route[] routes; - + private Routes(final Configuration configuration, final AbstractScript patternScript, final String pattern, final Route... routes) { this.configuration = configuration; this.patternScript = patternScript; @@ -156,21 +157,17 @@ public final class Routes { this.routes = routes; } - public Bindings getBindings() { - return bindings; - } - /** * Returns the pattern. * @param event The log event passed to the script (if there is a script.) + * @param scriptStaticVariables The script's static variables. * @return the pattern. */ - public String getPattern(final LogEvent event) { + public String getPattern(final LogEvent event, ConcurrentMap<Object, Object> scriptStaticVariables) { if (patternScript != null) { final ScriptManager scriptManager = configuration.getScriptManager(); - if (bindings == null) { - bindings = scriptManager.createBindings(patternScript); - } + final Bindings bindings = scriptManager.createBindings(patternScript); + bindings.put(STATIC_VARIABLES_KEY, scriptStaticVariables); bindings.put(LOG_EVENT_KEY, event); final Object object = scriptManager.execute(patternScript.getName(), bindings); bindings.remove(LOG_EVENT_KEY); @@ -204,10 +201,6 @@ public final class Routes { return routes; } - public void setBindings(final Bindings bindings) { - this.bindings = bindings; - } - @Override public String toString() { final StringBuilder sb = new StringBuilder("{"); http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/2d18d39c/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/RoutingAppender.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/RoutingAppender.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/RoutingAppender.java index e823484..49cc600 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/RoutingAppender.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/appender/routing/RoutingAppender.java @@ -52,6 +52,8 @@ import org.apache.logging.log4j.core.util.Booleans; @Plugin(name = "Routing", category = "Core", elementType = "appender", printObject = true) public final class RoutingAppender extends AbstractAppender { + public static final String STATIC_VARIABLES_KEY = "staticVariables"; + public static class Builder<B extends Builder<B>> extends AbstractAppender.Builder<B> implements org.apache.logging.log4j.core.util.Builder<RoutingAppender> { @@ -146,7 +148,7 @@ public final class RoutingAppender extends AbstractAppender { private final RewritePolicy rewritePolicy; private final PurgePolicy purgePolicy; private final AbstractScript defaultRouteScript; - private Bindings bindings; + private final ConcurrentMap<Object, Object> scriptStaticVariables = new ConcurrentHashMap<>(); private RoutingAppender(final String name, final Filter filter, final boolean ignoreExceptions, final Routes routes, final RewritePolicy rewritePolicy, final Configuration configuration, final PurgePolicy purgePolicy, @@ -181,8 +183,8 @@ public final class RoutingAppender extends AbstractAppender { } else { final ScriptManager scriptManager = configuration.getScriptManager(); scriptManager.addScript(defaultRouteScript); - bindings = scriptManager.createBindings(defaultRouteScript); - routes.setBindings(bindings); + final Bindings bindings = scriptManager.createBindings(defaultRouteScript); + bindings.put(STATIC_VARIABLES_KEY, scriptStaticVariables); final Object object = scriptManager.execute(defaultRouteScript.getName(), bindings); final Route route = routes.getRoute(Objects.toString(object, null)); if (route != null) { @@ -225,7 +227,7 @@ public final class RoutingAppender extends AbstractAppender { if (rewritePolicy != null) { event = rewritePolicy.rewrite(event); } - final String pattern = routes.getPattern(event); + final String pattern = routes.getPattern(event, scriptStaticVariables); final String key = pattern != null ? configuration.getStrSubstitutor().replace(event, pattern) : defaultRoute.getKey(); final AppenderControl control = getControl(key, event); if (control != null) { @@ -365,7 +367,7 @@ public final class RoutingAppender extends AbstractAppender { return configuration; } - public Bindings getBindings() { - return bindings; + public ConcurrentMap<Object, Object> getScriptStaticVariables() { + return scriptStaticVariables; } } http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/2d18d39c/log4j-core/src/main/java/org/apache/logging/log4j/core/script/ScriptManager.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/script/ScriptManager.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/script/ScriptManager.java index ccb7993..3e274c9 100644 --- a/log4j-core/src/main/java/org/apache/logging/log4j/core/script/ScriptManager.java +++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/script/ScriptManager.java @@ -1,279 +1,280 @@ -/* - * 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.logging.log4j.core.script; - -import java.io.File; -import java.io.Serializable; -import java.nio.file.Path; -import java.security.AccessController; -import java.security.PrivilegedAction; -import java.util.List; -import java.util.concurrent.ConcurrentHashMap; -import java.util.concurrent.ConcurrentMap; - -import javax.script.Bindings; -import javax.script.Compilable; -import javax.script.CompiledScript; -import javax.script.ScriptEngine; -import javax.script.ScriptEngineFactory; -import javax.script.ScriptEngineManager; -import javax.script.ScriptException; -import javax.script.SimpleBindings; - -import org.apache.logging.log4j.Logger; -import org.apache.logging.log4j.core.config.Configuration; -import org.apache.logging.log4j.core.util.FileWatcher; -import org.apache.logging.log4j.core.util.WatchManager; -import org.apache.logging.log4j.status.StatusLogger; - -/** - * Manages the scripts use by the Configuration. - */ -public class ScriptManager implements FileWatcher, Serializable { - - private abstract class AbstractScriptRunner implements ScriptRunner { - private final ConcurrentMap<Object, Object> scriptStaticVariables = new ConcurrentHashMap<>(); - - @Override - public Bindings createBindings() { - final SimpleBindings bindings = new SimpleBindings(); - bindings.put("configuration", configuration); - bindings.put("statusLogger", logger); - bindings.put("staticVariables", scriptStaticVariables); - return bindings; - } - - } - - private static final long serialVersionUID = -2534169384971965196L; - private static final String KEY_THREADING = "THREADING"; - private static final Logger logger = StatusLogger.getLogger(); - - private final Configuration configuration; - private final ScriptEngineManager manager = new ScriptEngineManager(); - private final ConcurrentMap<String, ScriptRunner> scriptRunners = new ConcurrentHashMap<>(); - private final String languages; - private final WatchManager watchManager; - - public ScriptManager(final Configuration configuration, final WatchManager watchManager) { - this.configuration = configuration; - this.watchManager = watchManager; - final List<ScriptEngineFactory> factories = manager.getEngineFactories(); - if (logger.isDebugEnabled()) { - final StringBuilder sb = new StringBuilder(); - logger.debug("Installed script engines"); - for (final ScriptEngineFactory factory : factories) { - String threading = (String) factory.getParameter(KEY_THREADING); - if (threading == null) { - threading = "Not Thread Safe"; - } - final StringBuilder names = new StringBuilder(); - for (final String name : factory.getNames()) { - if (names.length() > 0) { - names.append(", "); - } - names.append(name); - } - if (sb.length() > 0) { - sb.append(", "); - } - sb.append(names); - final boolean compiled = factory.getScriptEngine() instanceof Compilable; - logger.debug(factory.getEngineName() + " Version: " + factory.getEngineVersion() + - ", Language: " + factory.getLanguageName() + ", Threading: " + threading + - ", Compile: " + compiled + ", Names: {" + names.toString() + "}"); - } - languages = sb.toString(); - } else { - final StringBuilder names = new StringBuilder(); - for (final ScriptEngineFactory factory : factories) { - for (final String name : factory.getNames()) { - if (names.length() > 0) { - names.append(", "); - } - names.append(name); - } - } - languages = names.toString(); - } - } - - public void addScript(final AbstractScript script) { - final ScriptEngine engine = manager.getEngineByName(script.getLanguage()); - if (engine == null) { - logger.error("No ScriptEngine found for language " + script.getLanguage() + ". Available languages are: " + - languages); - return; - } - if (engine.getFactory().getParameter(KEY_THREADING) == null) { - scriptRunners.put(script.getName(), new ThreadLocalScriptRunner(script)); - } else { - scriptRunners.put(script.getName(), new MainScriptRunner(engine, script)); - } - - if (script instanceof ScriptFile) { - final ScriptFile scriptFile = (ScriptFile) script; - final Path path = scriptFile.getPath(); - if (scriptFile.isWatched() && path != null) { - watchManager.watchFile(path.toFile(), this); - } - } - } - - public Bindings createBindings(AbstractScript script) { - return getScriptRunner(script).createBindings(); - } - - public AbstractScript getScript(final String name) { - final ScriptRunner runner = scriptRunners.get(name); - return runner != null ? runner.getScript() : null; - } - - @Override - public void fileModified(final File file) { - final ScriptRunner runner = scriptRunners.get(file.toString()); - if (runner == null) { - logger.info("{} is not a running script"); - return; - } - final ScriptEngine engine = runner.getScriptEngine(); - final AbstractScript script = runner.getScript(); - if (engine.getFactory().getParameter(KEY_THREADING) == null) { - scriptRunners.put(script.getName(), new ThreadLocalScriptRunner(script)); - } else { - scriptRunners.put(script.getName(), new MainScriptRunner(engine, script)); - } - - } - - public Object execute(final String name, final Bindings bindings) { - final ScriptRunner scriptRunner = scriptRunners.get(name); - if (scriptRunner == null) { - logger.warn("No script named {} could be found"); - return null; - } - return AccessController.doPrivileged(new PrivilegedAction<Object>() { - @Override - public Object run() { - return scriptRunner.execute(bindings); - } - }); - } - - private interface ScriptRunner { - - Bindings createBindings(); - - Object execute(Bindings bindings); - - AbstractScript getScript(); - - ScriptEngine getScriptEngine(); - } - - private class MainScriptRunner extends AbstractScriptRunner { - private final AbstractScript script; - private final CompiledScript compiledScript; - private final ScriptEngine scriptEngine; - - public MainScriptRunner(final ScriptEngine scriptEngine, final AbstractScript script) { - this.script = script; - this.scriptEngine = scriptEngine; - CompiledScript compiled = null; - if (scriptEngine instanceof Compilable) { - logger.debug("Script {} is compilable", script.getName()); - compiled = AccessController.doPrivileged(new PrivilegedAction<CompiledScript>() { - @Override - public CompiledScript run() { - try { - return ((Compilable) scriptEngine).compile(script.getScriptText()); - } catch (final Throwable ex) { - /* ScriptException is what really should be caught here. However, beanshell's - * ScriptEngine implements Compilable but then throws Error when the compile method - * is called! - */ - logger.warn("Error compiling script", ex); - return null; - } - } - }); - } - compiledScript = compiled; - } - - @Override - public ScriptEngine getScriptEngine() { - return this.scriptEngine; - } - - @Override - public Object execute(final Bindings bindings) { - if (compiledScript != null) { - try { - return compiledScript.eval(bindings); - } catch (final ScriptException ex) { - logger.error("Error running script " + script.getName(), ex); - return null; - } - } - try { - return scriptEngine.eval(script.getScriptText(), bindings); - } catch (final ScriptException ex) { - logger.error("Error running script " + script.getName(), ex); - return null; - } - } - - @Override - public AbstractScript getScript() { - return script; - } - } - - private class ThreadLocalScriptRunner extends AbstractScriptRunner { - private final AbstractScript script; - - private final ThreadLocal<MainScriptRunner> runners = new ThreadLocal<MainScriptRunner>() { - @Override protected MainScriptRunner initialValue() { - final ScriptEngine engine = manager.getEngineByName(script.getLanguage()); - return new MainScriptRunner(engine, script); - } - }; - - public ThreadLocalScriptRunner(final AbstractScript script) { - this.script = script; - } - - @Override - public Object execute(final Bindings bindings) { - return runners.get().execute(bindings); - } - - @Override - public AbstractScript getScript() { - return script; - } - @Override - public ScriptEngine getScriptEngine() { - return runners.get().getScriptEngine(); - } - } - - private ScriptRunner getScriptRunner(AbstractScript script) { - return scriptRunners.get(script.getName()); - } -} +/* + * 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.logging.log4j.core.script; + +import java.io.File; +import java.io.Serializable; +import java.nio.file.Path; +import java.security.AccessController; +import java.security.PrivilegedAction; +import java.util.List; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; + +import javax.script.Bindings; +import javax.script.Compilable; +import javax.script.CompiledScript; +import javax.script.ScriptEngine; +import javax.script.ScriptEngineFactory; +import javax.script.ScriptEngineManager; +import javax.script.ScriptException; +import javax.script.SimpleBindings; + +import org.apache.logging.log4j.Logger; +import org.apache.logging.log4j.core.config.Configuration; +import org.apache.logging.log4j.core.util.FileWatcher; +import org.apache.logging.log4j.core.util.WatchManager; +import org.apache.logging.log4j.status.StatusLogger; + +/** + * Manages the scripts use by the Configuration. + */ +public class ScriptManager implements FileWatcher, Serializable { + + private abstract class AbstractScriptRunner implements ScriptRunner { + + private static final String KEY_STATUS_LOGGER = "statusLogger"; + private static final String KEY_CONFIGURATION = "configuration"; + + @Override + public Bindings createBindings() { + final SimpleBindings bindings = new SimpleBindings(); + bindings.put(KEY_CONFIGURATION, configuration); + bindings.put(KEY_STATUS_LOGGER, logger); + return bindings; + } + + } + + private static final long serialVersionUID = -2534169384971965196L; + private static final String KEY_THREADING = "THREADING"; + private static final Logger logger = StatusLogger.getLogger(); + + private final Configuration configuration; + private final ScriptEngineManager manager = new ScriptEngineManager(); + private final ConcurrentMap<String, ScriptRunner> scriptRunners = new ConcurrentHashMap<>(); + private final String languages; + private final WatchManager watchManager; + + public ScriptManager(final Configuration configuration, final WatchManager watchManager) { + this.configuration = configuration; + this.watchManager = watchManager; + final List<ScriptEngineFactory> factories = manager.getEngineFactories(); + if (logger.isDebugEnabled()) { + final StringBuilder sb = new StringBuilder(); + logger.debug("Installed script engines"); + for (final ScriptEngineFactory factory : factories) { + String threading = (String) factory.getParameter(KEY_THREADING); + if (threading == null) { + threading = "Not Thread Safe"; + } + final StringBuilder names = new StringBuilder(); + for (final String name : factory.getNames()) { + if (names.length() > 0) { + names.append(", "); + } + names.append(name); + } + if (sb.length() > 0) { + sb.append(", "); + } + sb.append(names); + final boolean compiled = factory.getScriptEngine() instanceof Compilable; + logger.debug(factory.getEngineName() + " Version: " + factory.getEngineVersion() + + ", Language: " + factory.getLanguageName() + ", Threading: " + threading + + ", Compile: " + compiled + ", Names: {" + names.toString() + "}"); + } + languages = sb.toString(); + } else { + final StringBuilder names = new StringBuilder(); + for (final ScriptEngineFactory factory : factories) { + for (final String name : factory.getNames()) { + if (names.length() > 0) { + names.append(", "); + } + names.append(name); + } + } + languages = names.toString(); + } + } + + public void addScript(final AbstractScript script) { + final ScriptEngine engine = manager.getEngineByName(script.getLanguage()); + if (engine == null) { + logger.error("No ScriptEngine found for language " + script.getLanguage() + ". Available languages are: " + + languages); + return; + } + if (engine.getFactory().getParameter(KEY_THREADING) == null) { + scriptRunners.put(script.getName(), new ThreadLocalScriptRunner(script)); + } else { + scriptRunners.put(script.getName(), new MainScriptRunner(engine, script)); + } + + if (script instanceof ScriptFile) { + final ScriptFile scriptFile = (ScriptFile) script; + final Path path = scriptFile.getPath(); + if (scriptFile.isWatched() && path != null) { + watchManager.watchFile(path.toFile(), this); + } + } + } + + public Bindings createBindings(AbstractScript script) { + return getScriptRunner(script).createBindings(); + } + + public AbstractScript getScript(final String name) { + final ScriptRunner runner = scriptRunners.get(name); + return runner != null ? runner.getScript() : null; + } + + @Override + public void fileModified(final File file) { + final ScriptRunner runner = scriptRunners.get(file.toString()); + if (runner == null) { + logger.info("{} is not a running script"); + return; + } + final ScriptEngine engine = runner.getScriptEngine(); + final AbstractScript script = runner.getScript(); + if (engine.getFactory().getParameter(KEY_THREADING) == null) { + scriptRunners.put(script.getName(), new ThreadLocalScriptRunner(script)); + } else { + scriptRunners.put(script.getName(), new MainScriptRunner(engine, script)); + } + + } + + public Object execute(final String name, final Bindings bindings) { + final ScriptRunner scriptRunner = scriptRunners.get(name); + if (scriptRunner == null) { + logger.warn("No script named {} could be found"); + return null; + } + return AccessController.doPrivileged(new PrivilegedAction<Object>() { + @Override + public Object run() { + return scriptRunner.execute(bindings); + } + }); + } + + private interface ScriptRunner { + + Bindings createBindings(); + + Object execute(Bindings bindings); + + AbstractScript getScript(); + + ScriptEngine getScriptEngine(); + } + + private class MainScriptRunner extends AbstractScriptRunner { + private final AbstractScript script; + private final CompiledScript compiledScript; + private final ScriptEngine scriptEngine; + + public MainScriptRunner(final ScriptEngine scriptEngine, final AbstractScript script) { + this.script = script; + this.scriptEngine = scriptEngine; + CompiledScript compiled = null; + if (scriptEngine instanceof Compilable) { + logger.debug("Script {} is compilable", script.getName()); + compiled = AccessController.doPrivileged(new PrivilegedAction<CompiledScript>() { + @Override + public CompiledScript run() { + try { + return ((Compilable) scriptEngine).compile(script.getScriptText()); + } catch (final Throwable ex) { + /* ScriptException is what really should be caught here. However, beanshell's + * ScriptEngine implements Compilable but then throws Error when the compile method + * is called! + */ + logger.warn("Error compiling script", ex); + return null; + } + } + }); + } + compiledScript = compiled; + } + + @Override + public ScriptEngine getScriptEngine() { + return this.scriptEngine; + } + + @Override + public Object execute(final Bindings bindings) { + if (compiledScript != null) { + try { + return compiledScript.eval(bindings); + } catch (final ScriptException ex) { + logger.error("Error running script " + script.getName(), ex); + return null; + } + } + try { + return scriptEngine.eval(script.getScriptText(), bindings); + } catch (final ScriptException ex) { + logger.error("Error running script " + script.getName(), ex); + return null; + } + } + + @Override + public AbstractScript getScript() { + return script; + } + } + + private class ThreadLocalScriptRunner extends AbstractScriptRunner { + private final AbstractScript script; + + private final ThreadLocal<MainScriptRunner> runners = new ThreadLocal<MainScriptRunner>() { + @Override protected MainScriptRunner initialValue() { + final ScriptEngine engine = manager.getEngineByName(script.getLanguage()); + return new MainScriptRunner(engine, script); + } + }; + + public ThreadLocalScriptRunner(final AbstractScript script) { + this.script = script; + } + + @Override + public Object execute(final Bindings bindings) { + return runners.get().execute(bindings); + } + + @Override + public AbstractScript getScript() { + return script; + } + @Override + public ScriptEngine getScriptEngine() { + return runners.get().getScriptEngine(); + } + } + + private ScriptRunner getScriptRunner(AbstractScript script) { + return scriptRunners.get(script.getName()); + } +} http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/2d18d39c/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/DefaultRouteScriptAppenderTest.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/DefaultRouteScriptAppenderTest.java b/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/DefaultRouteScriptAppenderTest.java index 670395b..b77d12f 100644 --- a/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/DefaultRouteScriptAppenderTest.java +++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/DefaultRouteScriptAppenderTest.java @@ -21,8 +21,7 @@ import static org.junit.Assert.assertTrue; import java.util.List; import java.util.Map; - -import javax.script.Bindings; +import java.util.concurrent.ConcurrentMap; import org.apache.logging.log4j.Marker; import org.apache.logging.log4j.MarkerManager; @@ -67,10 +66,10 @@ public class DefaultRouteScriptAppenderTest { private void checkStaticVars() { final RoutingAppender routingAppender = getRoutingAppender(); - final Bindings bindings = routingAppender.getBindings(); + final ConcurrentMap<Object, Object> map = routingAppender.getScriptStaticVariables(); if (expectBindingEntries) { - Assert.assertEquals("TestValue2", ((Map<?, ?>) bindings.get("staticVariables")).get("TestKey")); - Assert.assertEquals("HEXDUMP", ((Map<?, ?>) bindings.get("staticVariables")).get("MarkerName")); + Assert.assertEquals("TestValue2", map.get("TestKey")); + Assert.assertEquals("HEXDUMP", map.get("MarkerName")); } } http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/2d18d39c/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/RoutesScriptAppenderTest.java ---------------------------------------------------------------------- diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/RoutesScriptAppenderTest.java b/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/RoutesScriptAppenderTest.java index 84d13a1..7e40234 100644 --- a/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/RoutesScriptAppenderTest.java +++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/appender/routing/RoutesScriptAppenderTest.java @@ -21,10 +21,16 @@ import static org.junit.Assert.assertTrue; import java.util.List; import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import org.apache.logging.log4j.Level; +import org.apache.logging.log4j.Marker; +import org.apache.logging.log4j.MarkerManager; import org.apache.logging.log4j.core.LogEvent; import org.apache.logging.log4j.core.Logger; import org.apache.logging.log4j.core.config.AppenderControl; +import org.apache.logging.log4j.core.impl.DefaultLogEventFactory; import org.apache.logging.log4j.junit.LoggerContextRule; import org.apache.logging.log4j.test.appender.ListAppender; import org.junit.Assert; @@ -39,20 +45,36 @@ import org.junit.runners.Parameterized; @RunWith(Parameterized.class) public class RoutesScriptAppenderTest { - @Parameterized.Parameters(name = "{0}") - public static String[] getParameters() { - return new String[] { - "log4j-routing-routes-script-groovy.xml", - "log4j-routing-routes-script-javascript.xml" }; + @Parameterized.Parameters(name = "{0} {1}") + public static Object[][] getParameters() { + // @formatter:off + return new Object[][] { + { "log4j-routing-routes-script-groovy.xml", false }, + { "log4j-routing-routes-script-javascript.xml", false }, + { "log4j-routing-script-staticvars-javascript.xml", true }, + { "log4j-routing-script-staticvars-groovy.xml", true }, + }; + // @formatter:on } @Rule public final LoggerContextRule loggerContextRule; - public RoutesScriptAppenderTest(final String configLocation) { + private final boolean expectBindingEntries; + + public RoutesScriptAppenderTest(final String configLocation, final boolean expectBindingEntries) { this.loggerContextRule = new LoggerContextRule(configLocation); + this.expectBindingEntries = expectBindingEntries; } + private void checkStaticVars() { + final RoutingAppender routingAppender = getRoutingAppender(); + final ConcurrentMap<Object, Object> map = routingAppender.getScriptStaticVariables(); + if (expectBindingEntries) { + Assert.assertEquals("TestValue2", map.get("TestKey")); + Assert.assertEquals("HEXDUMP", map.get("MarkerName")); + } + } private ListAppender getListAppender() { final String key = "Service2"; final RoutingAppender routingAppender = getRoutingAppender(); @@ -69,6 +91,7 @@ public class RoutesScriptAppenderTest { } private void logAndCheck() { + Marker marker = MarkerManager.getMarker("HEXDUMP"); final Logger logger = loggerContextRule.getLogger(RoutesScriptAppenderTest.class); logger.error("Hello"); final ListAppender listAppender = getListAppender(); @@ -77,6 +100,8 @@ public class RoutesScriptAppenderTest { assertTrue("Incorrect number of events. Expected 1, got " + list.size(), list.size() == 1); logger.error("World"); assertTrue("Incorrect number of events. Expected 2, got " + list.size(), list.size() == 2); + logger.error(marker, "DEADBEEF"); + assertTrue("Incorrect number of events. Expected 3, got " + list.size(), list.size() == 3); } @Test(expected = AssertionError.class) @@ -105,12 +130,14 @@ public class RoutesScriptAppenderTest { @Test public void testRoutingAppenderRoutes() { final RoutingAppender routingAppender = getRoutingAppender(); - Assert.assertNull(routingAppender.getDefaultRouteScript()); - Assert.assertNull(routingAppender.getDefaultRoute()); + Assert.assertEquals(expectBindingEntries, routingAppender.getDefaultRouteScript() != null); + Assert.assertEquals(expectBindingEntries, routingAppender.getDefaultRoute() != null); final Routes routes = routingAppender.getRoutes(); Assert.assertNotNull(routes); Assert.assertNotNull(routes.getPatternScript()); - Assert.assertEquals("Service2", routes.getPattern(null)); + final LogEvent logEvent = DefaultLogEventFactory.getInstance().createEvent("", null, "", Level.ERROR, null, + null, null); + Assert.assertEquals("Service2", routes.getPattern(logEvent, new ConcurrentHashMap<>())); } @Test @@ -121,10 +148,12 @@ public class RoutesScriptAppenderTest { @Test public void testRoutingPresence1() { logAndCheck(); + checkStaticVars(); } @Test public void testRoutingPresence2() { logAndCheck(); + checkStaticVars(); } }
