You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@logging.apache.org by mi...@apache.org on 2016/10/21 20:34:22 UTC
logging-log4j2 git commit: Immutable empty StringMap
Repository: logging-log4j2
Updated Branches:
refs/heads/LOG4J2-1645 [created] a2a78643b
Immutable empty StringMap
Project: http://git-wip-us.apache.org/repos/asf/logging-log4j2/repo
Commit: http://git-wip-us.apache.org/repos/asf/logging-log4j2/commit/a2a78643
Tree: http://git-wip-us.apache.org/repos/asf/logging-log4j2/tree/a2a78643
Diff: http://git-wip-us.apache.org/repos/asf/logging-log4j2/diff/a2a78643
Branch: refs/heads/LOG4J2-1645
Commit: a2a78643b44ce1a01bb47fa0e796672e860f1db5
Parents: 22369cc
Author: Mikael St�ldal <mi...@staldal.nu>
Authored: Fri Oct 21 22:34:04 2016 +0200
Committer: Mikael St�ldal <mi...@staldal.nu>
Committed: Fri Oct 21 22:34:04 2016 +0200
----------------------------------------------------------------------
.../CopyOnWriteSortedArrayThreadContextMap.java | 8 +-
.../log4j/util/EmptyFrozenStringMap.java | 105 +++++++++++++++++++
.../log4j/core/impl/ContextDataFactory.java | 12 +++
.../core/impl/ThreadContextDataInjector.java | 10 +-
.../org/apache/logging/slf4j/MDCContextMap.java | 8 +-
src/changes/changes.xml | 3 +
6 files changed, 127 insertions(+), 19 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/log4j-api/src/main/java/org/apache/logging/log4j/spi/CopyOnWriteSortedArrayThreadContextMap.java
----------------------------------------------------------------------
diff --git a/log4j-api/src/main/java/org/apache/logging/log4j/spi/CopyOnWriteSortedArrayThreadContextMap.java b/log4j-api/src/main/java/org/apache/logging/log4j/spi/CopyOnWriteSortedArrayThreadContextMap.java
index ca2e22d..cd6d707 100644
--- a/log4j-api/src/main/java/org/apache/logging/log4j/spi/CopyOnWriteSortedArrayThreadContextMap.java
+++ b/log4j-api/src/main/java/org/apache/logging/log4j/spi/CopyOnWriteSortedArrayThreadContextMap.java
@@ -20,6 +20,7 @@ import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
+import org.apache.logging.log4j.util.EmptyFrozenStringMap;
import org.apache.logging.log4j.util.ReadOnlyStringMap;
import org.apache.logging.log4j.util.SortedArrayStringMap;
import org.apache.logging.log4j.util.StringMap;
@@ -52,11 +53,6 @@ class CopyOnWriteSortedArrayThreadContextMap implements ThreadContextMap2, CopyO
*/
protected static final String PROPERTY_NAME_INITIAL_CAPACITY = "log4j2.ThreadContext.initial.capacity";
- private static final StringMap EMPTY_CONTEXT_DATA = new SortedArrayStringMap();
- static {
- EMPTY_CONTEXT_DATA.freeze();
- }
-
private final ThreadLocal<StringMap> localMap;
public CopyOnWriteSortedArrayThreadContextMap() {
@@ -168,7 +164,7 @@ class CopyOnWriteSortedArrayThreadContextMap implements ThreadContextMap2, CopyO
@Override
public StringMap getReadOnlyContextData() {
final StringMap map = localMap.get();
- return map == null ? EMPTY_CONTEXT_DATA : map;
+ return map == null ? EmptyFrozenStringMap.INSTANCE : map;
}
@Override
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/log4j-api/src/main/java/org/apache/logging/log4j/util/EmptyFrozenStringMap.java
----------------------------------------------------------------------
diff --git a/log4j-api/src/main/java/org/apache/logging/log4j/util/EmptyFrozenStringMap.java b/log4j-api/src/main/java/org/apache/logging/log4j/util/EmptyFrozenStringMap.java
new file mode 100644
index 0000000..b0a3ff8
--- /dev/null
+++ b/log4j-api/src/main/java/org/apache/logging/log4j/util/EmptyFrozenStringMap.java
@@ -0,0 +1,105 @@
+/*
+ * 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.util;
+
+import java.util.Collections;
+import java.util.Map;
+
+/**
+ * <em>Consider this class private.</em>
+ * Empty pre-frozen implementation of the {@link StringMap} interface.
+ *
+ * @since 2.7.1
+ */
+public class EmptyFrozenStringMap implements StringMap {
+
+ /**
+ * Singleton instance.
+ */
+ public static final EmptyFrozenStringMap INSTANCE = new EmptyFrozenStringMap();
+
+ private static final String FROZEN = "Frozen collection cannot be modified";
+
+ /**
+ * Private default constructor to enforce singleton.
+ */
+ private EmptyFrozenStringMap() {
+ }
+
+ @Override
+ public Map<String, String> toMap() {
+ return Collections.emptyMap();
+ }
+
+ @Override
+ public boolean containsKey(String key) {
+ return false;
+ }
+
+ @Override
+ public <V> void forEach(BiConsumer<String, ? super V> action) {
+ }
+
+ @Override
+ public <V, S> void forEach(TriConsumer<String, ? super V, S> action, S state) {
+ }
+
+ @Override
+ public <V> V getValue(String key) {
+ return null;
+ }
+
+ @Override
+ public boolean isEmpty() {
+ return true;
+ }
+
+ @Override
+ public int size() {
+ return 0;
+ }
+
+ @Override
+ public void clear() {
+ }
+
+ @Override
+ public void freeze() {
+ }
+
+ @Override
+ public boolean isFrozen() {
+ return true;
+ }
+
+ @Override
+ public void putAll(ReadOnlyStringMap source) {
+ if (source == this || source.isEmpty()) { // throw NPE if null
+ return; // this.putAll(this) does not modify this collection
+ }
+ throw new UnsupportedOperationException(FROZEN);
+ }
+
+ @Override
+ public void putValue(String key, Object value) {
+ throw new UnsupportedOperationException(FROZEN);
+ }
+
+ @Override
+ public void remove(String key) {
+ }
+}
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ContextDataFactory.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ContextDataFactory.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ContextDataFactory.java
index b417072..fc85932 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ContextDataFactory.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ContextDataFactory.java
@@ -20,6 +20,7 @@ import java.lang.reflect.Constructor;
import org.apache.logging.log4j.core.ContextDataInjector;
import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.util.EmptyFrozenStringMap;
import org.apache.logging.log4j.util.LoaderUtil;
import org.apache.logging.log4j.util.PropertiesUtil;
import org.apache.logging.log4j.util.SortedArrayStringMap;
@@ -92,4 +93,15 @@ public class ContextDataFactory {
return new SortedArrayStringMap(initialCapacity);
}
}
+
+ /**
+ * An empty pre-frozen StringMap. The returned object may be shared.
+ * <p>
+ * Not affected by the system property {@code "log4j2.ContextData"}.
+ *
+ * @return an empty pre-frozen StringMap
+ */
+ public static StringMap emptyFrozenContextData() {
+ return EmptyFrozenStringMap.INSTANCE;
+ }
}
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ThreadContextDataInjector.java
----------------------------------------------------------------------
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ThreadContextDataInjector.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ThreadContextDataInjector.java
index 210c5da..192fe4d 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ThreadContextDataInjector.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/impl/ThreadContextDataInjector.java
@@ -43,7 +43,7 @@ import org.apache.logging.log4j.util.StringMap;
* @see ContextDataInjectorFactory
* @since 2.7
*/
-public class ThreadContextDataInjector {
+public class ThreadContextDataInjector {
/**
* Default {@code ContextDataInjector} for the legacy {@code Map<String, String>}-based ThreadContext (which is
@@ -52,10 +52,6 @@ public class ThreadContextDataInjector {
* This injector always puts key-value pairs into the specified reusable StringMap.
*/
public static class ForDefaultThreadContextMap implements ContextDataInjector {
- private static final StringMap EMPTY_STRING_MAP = ContextDataFactory.createContextData();
- static {
- EMPTY_STRING_MAP.freeze();
- }
/**
* Puts key-value pairs from both the specified list of properties as well as the thread context into the
@@ -77,7 +73,7 @@ public class ThreadContextDataInjector {
if (props == null || props.isEmpty()) {
// this will replace the LogEvent's context data with the returned instance.
// NOTE: must mark as frozen or downstream components may attempt to modify (UnsupportedOperationEx)
- return copy.isEmpty() ? EMPTY_STRING_MAP : frozenStringMap(copy);
+ return copy.isEmpty() ? ContextDataFactory.emptyFrozenContextData() : frozenStringMap(copy);
}
// If the list of Properties is non-empty we need to combine the properties and the ThreadContext
// data. Note that we cannot reuse the specified StringMap: some Loggers may have properties defined
@@ -106,7 +102,7 @@ public class ThreadContextDataInjector {
if (map instanceof ReadOnlyStringMap) {
return (ReadOnlyStringMap) map;
}
- return map.isEmpty() ? EMPTY_STRING_MAP : new JdkMapAdapterStringMap(map.getImmutableMapOrNull());
+ return map.isEmpty() ? ContextDataFactory.emptyFrozenContextData() : new JdkMapAdapterStringMap(map.getImmutableMapOrNull());
}
}
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/log4j-to-slf4j/src/main/java/org/apache/logging/slf4j/MDCContextMap.java
----------------------------------------------------------------------
diff --git a/log4j-to-slf4j/src/main/java/org/apache/logging/slf4j/MDCContextMap.java b/log4j-to-slf4j/src/main/java/org/apache/logging/slf4j/MDCContextMap.java
index 6b0f3ae..cb3a349 100644
--- a/log4j-to-slf4j/src/main/java/org/apache/logging/slf4j/MDCContextMap.java
+++ b/log4j-to-slf4j/src/main/java/org/apache/logging/slf4j/MDCContextMap.java
@@ -19,6 +19,7 @@ package org.apache.logging.slf4j;
import java.util.Map;
import java.util.Map.Entry;
+import org.apache.logging.log4j.util.EmptyFrozenStringMap;
import org.apache.logging.log4j.util.StringMap;
import org.apache.logging.log4j.spi.ThreadContextMap2;
import org.apache.logging.log4j.util.SortedArrayStringMap;
@@ -29,11 +30,6 @@ import org.slf4j.MDC;
*/
public class MDCContextMap implements ThreadContextMap2 {
- private static final StringMap EMPTY_CONTEXT_DATA = new SortedArrayStringMap();
- static {
- EMPTY_CONTEXT_DATA.freeze();
- }
-
@Override
public void put(final String key, final String value) {
MDC.put(key, value);
@@ -87,7 +83,7 @@ public class MDCContextMap implements ThreadContextMap2 {
public StringMap getReadOnlyContextData() {
final Map<String, String> copy = getCopy();
if (copy.isEmpty()) {
- return EMPTY_CONTEXT_DATA;
+ return EmptyFrozenStringMap.INSTANCE;
}
final StringMap result = new SortedArrayStringMap();
for (Entry<String, String> entry : copy.entrySet()) {
http://git-wip-us.apache.org/repos/asf/logging-log4j2/blob/a2a78643/src/changes/changes.xml
----------------------------------------------------------------------
diff --git a/src/changes/changes.xml b/src/changes/changes.xml
index 2922511..412164a 100644
--- a/src/changes/changes.xml
+++ b/src/changes/changes.xml
@@ -24,6 +24,9 @@
</properties>
<body>
<release version="2.7.1" date="2016-MM-DD" description="GA Release 2.7.1">
+ <action issue="LOG4J2-1645" dev="mikes" type="fix">
+ Immutable empty StringMap.
+ </action>
<action issue="LOG4J2-1623" dev="mikes" type="fix">
Configurable JVM shutdown hook timeout.
</action>