You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@logging.apache.org by rg...@apache.org on 2019/06/15 21:01:01 UTC
[logging-log4j2] 01/07: LOG4J2-2621 - Initial commit
This is an automated email from the ASF dual-hosted git repository.
rgoers pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/logging-log4j2.git
commit 8076a70a9e33db48fd68699c42a5262c4cb92fe0
Author: Ralph Goers <rg...@apache.org>
AuthorDate: Sun Jun 2 13:18:36 2019 -0700
LOG4J2-2621 - Initial commit
---
.../org/apache/logging/log4j}/util/Assert.java | 0
.../logging/log4j/util/InternalException.java | 56 ++++
.../org/apache/logging/log4j}/util/NameUtil.java | 0
.../apache/logging/log4j}/util/ReflectionUtil.java | 6 +-
.../log4j/junit/AbstractExternalFileCleaner.java | 0
.../org/apache/logging/log4j/junit/CleanFiles.java | 0
.../apache/logging/log4j/junit/CleanFolders.java | 0
.../log4j/junit/URLStreamHandlerFactoryRule.java | 0
.../org/apache/logging/log4j}/util/AssertTest.java | 2 +-
.../config/plugins/convert/Base64Converter.java | 79 -----
...TypeConverters.java => CoreTypeConverters.java} | 7 +-
.../ValidatingPluginWithGenericBuilderTest.java | 10 +-
log4j-plugins-java9/pom.xml | 157 +++++++++
log4j-plugins-java9/src/assembly/java9.xml | 40 +++
.../src/main/java/module-info.java | 15 +-
.../org/apache/logging/log4j/plugins/Dummy.java | 9 +-
.../logging/log4j/plugins/convert/Dummy.java | 9 +-
.../log4j/plugins/processor/PluginService.java | 9 +-
.../apache/logging/log4j/plugins/util/Dummy.java | 9 +-
.../logging/log4j/plugins/validation/Dummy.java | 9 +-
.../logging/log4j/plugins/visitors/Dummy.java | 9 +-
log4j-plugins/pom.xml | 360 +++++++++++++++++++++
.../org/apache/logging/log4j/plugins}/Node.java | 6 +-
.../org/apache/logging/log4j}/plugins/Plugin.java | 6 +-
.../logging/log4j}/plugins/PluginAliases.java | 4 +-
.../logging/log4j}/plugins/PluginAttribute.java | 8 +-
.../log4j}/plugins/PluginBuilderAttribute.java | 8 +-
.../log4j}/plugins/PluginBuilderFactory.java | 2 +-
.../logging/log4j}/plugins/PluginElement.java | 6 +-
.../logging/log4j}/plugins/PluginFactory.java | 2 +-
.../apache/logging/log4j}/plugins/PluginNode.java | 6 +-
.../apache/logging/log4j}/plugins/PluginValue.java | 6 +-
.../log4j}/plugins/PluginVisitorStrategy.java | 8 +-
.../log4j}/plugins/convert/EnumConverter.java | 2 +-
.../log4j}/plugins/convert/HexConverter.java | 2 +-
.../log4j}/plugins/convert/TypeConverter.java | 2 +-
.../plugins/convert/TypeConverterRegistry.java | 23 +-
.../log4j}/plugins/convert/TypeConverters.java | 47 +--
.../log4j/plugins/convert}/package-info.java | 7 +-
.../logging/log4j/plugins/osgi/Activator.java | 103 ++++++
.../logging/log4j/plugins/osgi}/package-info.java | 6 +-
.../logging/log4j/plugins}/package-info.java | 6 +-
.../log4j}/plugins/processor/PluginCache.java | 30 +-
.../log4j}/plugins/processor/PluginEntry.java | 14 +-
.../log4j}/plugins/processor/PluginProcessor.java | 157 +++++++--
.../log4j/plugins/processor/PluginService.java | 56 ++++
.../log4j}/plugins/processor/package-info.java | 2 +-
.../logging/log4j/plugins}/util/Builder.java | 4 +-
.../logging/log4j}/plugins/util/PluginManager.java | 8 +-
.../log4j}/plugins/util/PluginRegistry.java | 81 +++--
.../logging/log4j}/plugins/util/PluginType.java | 6 +-
.../logging/log4j}/plugins/util/ResolverUtil.java | 29 +-
.../logging/log4j/plugins/util/TypeUtil.java | 217 +++++++++++++
.../logging/log4j/plugins/util}/package-info.java | 2 +-
.../log4j}/plugins/validation/Constraint.java | 9 +-
.../plugins/validation/ConstraintValidator.java | 2 +-
.../plugins/validation/ConstraintValidators.java | 8 +-
.../plugins/validation/constraints/Required.java | 12 +-
.../plugins/validation/constraints/ValidHost.java | 6 +-
.../plugins/validation/constraints/ValidPort.java | 12 +-
.../validation/constraints/package-info.java | 2 +-
.../log4j}/plugins/validation/package-info.java | 2 +-
.../validation/validators/RequiredValidator.java | 14 +-
.../validation/validators/ValidHostValidator.java | 6 +-
.../validation/validators/ValidPortValidator.java | 8 +-
.../validation/validators/package-info.java | 2 +-
.../plugins/visitors/AbstractPluginVisitor.java | 34 +-
.../plugins/visitors/PluginAttributeVisitor.java | 27 +-
.../visitors/PluginBuilderAttributeVisitor.java | 23 +-
.../plugins/visitors/PluginElementVisitor.java | 17 +-
.../log4j}/plugins/visitors/PluginNodeVisitor.java | 14 +-
.../plugins/visitors/PluginValueVisitor.java | 18 +-
.../log4j}/plugins/visitors/PluginVisitor.java | 36 +--
.../log4j}/plugins/visitors/PluginVisitors.java | 12 +-
.../log4j/plugins/visitors}/package-info.java | 9 +-
.../services/javax.annotation.processing.Processor | 2 +-
.../plugins/convert/TypeConverterRegistryTest.java | 4 +-
.../log4j}/plugins/processor/FakePlugin.java | 6 +-
.../plugins/processor/PluginProcessorTest.java | 26 +-
.../util/ResolverUtilCustomProtocolTest.java | 30 +-
.../log4j}/plugins/util/ResolverUtilTest.java | 76 +++--
.../AbstractPluginWithGenericBuilder.java | 6 +-
.../log4j}/plugins/validation/HostAndPort.java | 14 +-
.../PluginWithGenericSubclassFoo1Builder.java | 12 +-
.../plugins/validation/ValidatingPlugin.java | 16 +-
.../ValidatingPluginWithGenericBuilder.java | 17 +-
.../ValidatingPluginWithTypedBuilder.java | 16 +-
.../resources/customplugin/FixedString.java.source | 37 ++-
.../log4j+config+with+plus+characters.xml | 31 ++
.../log4j+config+with+plus+characters.xml | 31 ++
90 files changed, 1655 insertions(+), 594 deletions(-)
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/Assert.java b/log4j-api/src/main/java/org/apache/logging/log4j/util/Assert.java
similarity index 100%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/util/Assert.java
rename to log4j-api/src/main/java/org/apache/logging/log4j/util/Assert.java
diff --git a/log4j-api/src/main/java/org/apache/logging/log4j/util/InternalException.java b/log4j-api/src/main/java/org/apache/logging/log4j/util/InternalException.java
new file mode 100644
index 0000000..8c433db
--- /dev/null
+++ b/log4j-api/src/main/java/org/apache/logging/log4j/util/InternalException.java
@@ -0,0 +1,56 @@
+/*
+ * 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;
+
+/**
+ * Exception thrown when an error occurs while logging. In most cases exceptions will be handled
+ * within Log4j but certain Appenders may be configured to allow exceptions to propagate to the
+ * application. This is a RuntimeException so that the exception may be thrown in those cases without
+ * requiring all Logger methods be contained with try/catch blocks.
+ */
+public class LoggingException extends RuntimeException {
+
+ private static final long serialVersionUID = 6366395965071580537L;
+
+ /**
+ * Construct an exception with a message.
+ *
+ * @param message The reason for the exception
+ */
+ public LoggingException(final String message) {
+ super(message);
+ }
+
+ /**
+ * Construct an exception with a message and underlying cause.
+ *
+ * @param message The reason for the exception
+ * @param cause The underlying cause of the exception
+ */
+ public LoggingException(final String message, final Throwable cause) {
+ super(message, cause);
+ }
+
+ /**
+ * Construct an exception with an underlying cause.
+ *
+ * @param cause The underlying cause of the exception
+ */
+ public LoggingException(final Throwable cause) {
+ super(cause);
+ }
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/NameUtil.java b/log4j-api/src/main/java/org/apache/logging/log4j/util/NameUtil.java
similarity index 100%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/util/NameUtil.java
rename to log4j-api/src/main/java/org/apache/logging/log4j/util/NameUtil.java
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/ReflectionUtil.java b/log4j-api/src/main/java/org/apache/logging/log4j/util/ReflectionUtil.java
similarity index 98%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/util/ReflectionUtil.java
rename to log4j-api/src/main/java/org/apache/logging/log4j/util/ReflectionUtil.java
index ffee439..f00e64a 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/ReflectionUtil.java
+++ b/log4j-api/src/main/java/org/apache/logging/log4j/util/ReflectionUtil.java
@@ -193,8 +193,10 @@ public final class ReflectionUtil {
} catch (final IllegalAccessException e) {
throw new IllegalStateException(e);
} catch (final InvocationTargetException e) {
- Throwables.rethrow(e.getCause());
- throw new InternalError("Unreachable");
+ if (e.getCause() instanceof RuntimeException) {
+ throw (RuntimeException) e.getCause();
+ }
+ throw new
}
}
}
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/junit/AbstractExternalFileCleaner.java b/log4j-api/src/test/java/org/apache/logging/log4j/junit/AbstractExternalFileCleaner.java
similarity index 100%
rename from log4j-core/src/test/java/org/apache/logging/log4j/junit/AbstractExternalFileCleaner.java
rename to log4j-api/src/test/java/org/apache/logging/log4j/junit/AbstractExternalFileCleaner.java
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/junit/CleanFiles.java b/log4j-api/src/test/java/org/apache/logging/log4j/junit/CleanFiles.java
similarity index 100%
rename from log4j-core/src/test/java/org/apache/logging/log4j/junit/CleanFiles.java
rename to log4j-api/src/test/java/org/apache/logging/log4j/junit/CleanFiles.java
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/junit/CleanFolders.java b/log4j-api/src/test/java/org/apache/logging/log4j/junit/CleanFolders.java
similarity index 100%
rename from log4j-core/src/test/java/org/apache/logging/log4j/junit/CleanFolders.java
rename to log4j-api/src/test/java/org/apache/logging/log4j/junit/CleanFolders.java
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/junit/URLStreamHandlerFactoryRule.java b/log4j-api/src/test/java/org/apache/logging/log4j/junit/URLStreamHandlerFactoryRule.java
similarity index 100%
rename from log4j-core/src/test/java/org/apache/logging/log4j/junit/URLStreamHandlerFactoryRule.java
rename to log4j-api/src/test/java/org/apache/logging/log4j/junit/URLStreamHandlerFactoryRule.java
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/util/AssertTest.java b/log4j-api/src/test/java/org/apache/logging/log4j/util/AssertTest.java
similarity index 99%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/util/AssertTest.java
rename to log4j-api/src/test/java/org/apache/logging/log4j/util/AssertTest.java
index 242c41e..7e46036 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/util/AssertTest.java
+++ b/log4j-api/src/test/java/org/apache/logging/log4j/util/AssertTest.java
@@ -65,4 +65,4 @@ public class AssertTest {
assertEquals(isEmpty, Assert.isEmpty(value));
}
-}
\ No newline at end of file
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/Base64Converter.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/Base64Converter.java
deleted file mode 100644
index f4e421f..0000000
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/Base64Converter.java
+++ /dev/null
@@ -1,79 +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.logging.log4j.core.config.plugins.convert;
-
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.status.StatusLogger;
-import org.apache.logging.log4j.util.LoaderUtil;
-
-/**
- * @Since 2.9
- */
-public class Base64Converter {
-
- private static final Logger LOGGER = StatusLogger.getLogger();
- private static Method method = null;
- private static Object decoder = null;
-
- static {
- try {
- // Base64 is available in Java 8 and up.
- Class<?> clazz = LoaderUtil.loadClass("java.util.Base64");
- final Method getDecoder = clazz.getMethod("getDecoder", (Class[]) null);
- decoder = getDecoder.invoke(null, (Object[]) null);
- clazz = decoder.getClass();
- method = clazz.getMethod("decode", String.class);
- } catch (final ClassNotFoundException ex) {
-
- } catch (final NoSuchMethodException ex) {
-
- } catch (final IllegalAccessException ex) {
-
- } catch (final InvocationTargetException ex) {
-
- }
- if (method == null) {
- try {
- // DatatypeConverter is not in the default module in Java 9.
- final Class<?> clazz = LoaderUtil.loadClass("javax.xml.bind.DatatypeConverter");
- method = clazz.getMethod("parseBase64Binary", String.class);
- } catch (final ClassNotFoundException ex) {
- LOGGER.error("No Base64 Converter is available");
- } catch (final NoSuchMethodException ex) {
-
- }
- }
- }
-
- public static byte[] parseBase64Binary(final String encoded) {
- if (method == null) {
- LOGGER.error("No base64 converter");
- } else {
- try {
- return (byte[]) method.invoke(decoder, encoded);
- } catch (final IllegalAccessException ex) {
- LOGGER.error("Error decoding string - " + ex.getMessage());
- } catch (final InvocationTargetException ex) {
- LOGGER.error("Error decoding string - " + ex.getMessage());
- }
- }
- return new byte[0];
- }
-}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java b/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/CoreTypeConverters.java
similarity index 98%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java
copy to log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/CoreTypeConverters.java
index dc833f0..00e6da7 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java
+++ b/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/CoreTypeConverters.java
@@ -30,13 +30,14 @@ import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.Provider;
import java.security.Security;
+import java.util.Base64;
import java.util.UUID;
import java.util.regex.Pattern;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.appender.rolling.action.Duration;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
+import org.apache.logging.log4j.plugins.Plugin;
import org.apache.logging.log4j.core.util.CronExpression;
import org.apache.logging.log4j.status.StatusLogger;
import org.apache.logging.log4j.util.LoaderUtil;
@@ -56,6 +57,8 @@ public final class TypeConverters {
*/
public static final String CATEGORY = "TypeConverter";
+ private static final Base64.Decoder decoder = Base64.getDecoder();
+
/**
* Parses a {@link String} into a {@link BigDecimal}.
*/
@@ -112,7 +115,7 @@ public final class TypeConverters {
bytes = new byte[0];
} else if (value.startsWith(PREFIX_BASE64)) {
final String lexicalXSDBase64Binary = value.substring(PREFIX_BASE64.length());
- bytes = Base64Converter.parseBase64Binary(lexicalXSDBase64Binary);
+ bytes = decoder.decode(lexicalXSDBase64Binary);
} else if (value.startsWith(PREFIX_0x)) {
final String lexicalXSDHexBinary = value.substring(PREFIX_0x.length());
bytes = HexConverter.parseHexBinary(lexicalXSDHexBinary);
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidatingPluginWithGenericBuilderTest.java b/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidatingPluginWithGenericBuilderTest.java
index 8ee5abb..27ac5fe 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidatingPluginWithGenericBuilderTest.java
+++ b/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidatingPluginWithGenericBuilderTest.java
@@ -20,12 +20,12 @@ import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
-import org.apache.logging.log4j.core.config.Node;
+import org.apache.logging.log4j.plugins.Node;
import org.apache.logging.log4j.core.config.NullConfiguration;
-import org.apache.logging.log4j.core.config.plugins.util.PluginBuilder;
-import org.apache.logging.log4j.core.config.plugins.util.PluginManager;
-import org.apache.logging.log4j.core.config.plugins.util.PluginType;
-import org.apache.logging.log4j.core.config.plugins.validation.ValidatingPluginWithGenericBuilder;
+import org.apache.logging.log4j.plugins.util.PluginBuilder;
+import org.apache.logging.log4j.plugins.util.PluginManager;
+import org.apache.logging.log4j.plugins.util.PluginType;
+import org.apache.logging.log4j.plugins.validation.ValidatingPluginWithGenericBuilder;
import org.junit.Before;
import org.junit.Test;
diff --git a/log4j-plugins-java9/pom.xml b/log4j-plugins-java9/pom.xml
new file mode 100644
index 0000000..49f81c6
--- /dev/null
+++ b/log4j-plugins-java9/pom.xml
@@ -0,0 +1,157 @@
+<?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.
+ -->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <parent>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j</artifactId>
+ <version>3.0.0-SNAPSHOT</version>
+ <relativePath>../</relativePath>
+ </parent>
+ <artifactId>log4j-plugins-java9</artifactId>
+ <packaging>pom</packaging>
+ <name>Apache Log4j Plugins Module support</name>
+ <description>Apache Log4j Plugin Moduels Support</description>
+ <properties>
+ <log4jParentDir>${basedir}/..</log4jParentDir>
+ <docLabel>Log4j Plugins Documentation</docLabel>
+ <projectDir>/plugins</projectDir>
+ </properties>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j-api</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.maven</groupId>
+ <artifactId>maven-core</artifactId>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-toolchains-plugin</artifactId>
+ <version>1.1</version>
+ <executions>
+ <execution>
+ <goals>
+ <goal>toolchain</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <toolchains>
+ <jdk>
+ <version>[9, )</version>
+ </jdk>
+ </toolchains>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>default-compile</id>
+ <phase>compile</phase>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ </execution>
+ <execution>
+ <id>default-test-compile</id>
+ <phase>test-compile</phase>
+ <goals>
+ <goal>testCompile</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <source>9</source>
+ <target>9</target>
+ <release>9</release>
+ <proc>none</proc>
+ <!-- disable errorprone -->
+ <compilerId>javac</compilerId>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <!-- Do not upgrade until https://issues.apache.org/jira/browse/SUREFIRE-720 is fixed -->
+ <version>2.13</version>
+ <executions>
+ <execution>
+ <id>test</id>
+ <phase>test</phase>
+ <goals>
+ <goal>test</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <systemPropertyVariables>
+ <java.awt.headless>true</java.awt.headless>
+ </systemPropertyVariables>
+ <includes>
+ <include>**/Test*.java</include>
+ <include>**/*Test.java</include>
+ </includes>
+ <excludes>
+ <exclude>**/*FuncTest.java</exclude>
+ </excludes>
+ </configuration>
+ </plugin>
+ <plugin>
+ <artifactId>maven-assembly-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>zip</id>
+ <phase>package</phase>
+ <goals>
+ <goal>single</goal>
+ </goals>
+ <configuration>
+ <finalName>log4j-plugins-java9-${project.version}</finalName>
+ <appendAssemblyId>false</appendAssemblyId>
+ <descriptors>
+ <descriptor>src/assembly/java9.xml</descriptor>
+ </descriptors>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <version>${deploy.plugin.version}</version>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+</project>
+
diff --git a/log4j-plugins-java9/src/assembly/java9.xml b/log4j-plugins-java9/src/assembly/java9.xml
new file mode 100644
index 0000000..34649d4
--- /dev/null
+++ b/log4j-plugins-java9/src/assembly/java9.xml
@@ -0,0 +1,40 @@
+<?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.
+-->
+
+<assembly>
+ <id>src</id>
+ <formats>
+ <format>zip</format>
+ </formats>
+ <baseDirectory>/</baseDirectory>
+ <fileSets>
+ <fileSet>
+ <directory>${project.build.outputDirectory}</directory>
+ <outputDirectory>/classes/META-INF/versions/9</outputDirectory>
+ <includes>
+ <include>module-info.class</include>
+ </includes>
+ <excludes>
+ <exclude>**/Dummy.class</exclude>
+ <exclude>**/PluginService.class</exclude>
+ </excludes>
+ </fileSet>
+ </fileSets>
+</assembly>
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/module-info.java
similarity index 65%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/module-info.java
index f22ba49..9802622 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/module-info.java
@@ -14,10 +14,13 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+module org.apache.logging.log4j.plugins {
+ exports org.apache.logging.log4j.plugins;
+ exports org.apache.logging.log4j.plugins.convert;
+ exports org.apache.logging.log4j.plugins.processor;
+ exports org.apache.logging.log4j.plugins.util;
+ exports org.apache.logging.log4j.plugins.validation;
+ exports org.apache.logging.log4j.plugins.visitors;
-/**
- * Validation annotations.
- *
- * @since 2.1
- */
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+ uses org.apache.logging.log4j.plugins.processor.PluginService;
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/Dummy.java
similarity index 80%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/Dummy.java
index f22ba49..14a90ed 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/Dummy.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class Dummy {
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/convert/Dummy.java
similarity index 79%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/convert/Dummy.java
index f22ba49..10923e8 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/convert/Dummy.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins.convert;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class Dummy {
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java
similarity index 79%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java
index f22ba49..b93ef59 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins.processor;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class PluginService {
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/util/Dummy.java
similarity index 80%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/util/Dummy.java
index f22ba49..5940b03 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/util/Dummy.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins.util;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class Dummy {
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/validation/Dummy.java
similarity index 79%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/validation/Dummy.java
index f22ba49..14882b5 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/validation/Dummy.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins.validation;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class Dummy {
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/visitors/Dummy.java
similarity index 79%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/visitors/Dummy.java
index f22ba49..5596338 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins-java9/src/main/java/org/apache/logging/log4j/plugins/visitors/Dummy.java
@@ -14,10 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
+package org.apache.logging.log4j.plugins.visitors;
/**
- * Validation annotations.
- *
- * @since 2.1
+ * This is a dummy class and is only here to allow module-info.java to compile. It will not
+ * be copied into the log4j-api module.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+public class Dummy {
+}
diff --git a/log4j-plugins/pom.xml b/log4j-plugins/pom.xml
new file mode 100644
index 0000000..3551d51
--- /dev/null
+++ b/log4j-plugins/pom.xml
@@ -0,0 +1,360 @@
+<?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.
+ -->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <parent>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j</artifactId>
+ <version>3.0.0-SNAPSHOT</version>
+ <relativePath>../</relativePath>
+ </parent>
+ <artifactId>log4j-plugins</artifactId>
+ <packaging>jar</packaging>
+ <name>Apache Log4j Plugins</name>
+ <description>Log4j Plugin Support</description>
+ <properties>
+ <log4jParentDir>${basedir}/..</log4jParentDir>
+ <docLabel>Plugin Documentation</docLabel>
+ <projectDir>/plugins</projectDir>
+ </properties>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j-api</artifactId>
+ </dependency>
+ <!-- Classes and resources to be shaded into the core jar -->
+ <dependency>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j-plugins-java9</artifactId>
+ <scope>provided</scope>
+ <type>zip</type>
+ </dependency>
+ <!-- Used for OSGi bundle support -->
+ <dependency>
+ <groupId>org.osgi</groupId>
+ <artifactId>org.osgi.core</artifactId>
+ <scope>provided</scope>
+ </dependency>
+
+ <!-- TEST DEPENDENCIES -->
+
+ <!-- Pull in useful test classes from API -->
+ <dependency>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j-api</artifactId>
+ <type>test-jar</type>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.hamcrest</groupId>
+ <artifactId>hamcrest-all</artifactId>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-dependency-plugin</artifactId>
+ <version>3.0.2</version>
+ <executions>
+ <execution>
+ <id>unpack-classes</id>
+ <phase>prepare-package</phase>
+ <goals>
+ <goal>unpack</goal>
+ </goals>
+ <configuration>
+ <artifactItems>
+ <artifactItem>
+ <groupId>org.apache.logging.log4j</groupId>
+ <artifactId>log4j-plugins-java9</artifactId>
+ <version>${project.version}</version>
+ <type>zip</type>
+ <overWrite>false</overWrite>
+ </artifactItem>
+ </artifactItems>
+ <includes>**/*.class</includes>
+ <excludes>**/*.java</excludes>
+ <outputDirectory>${project.build.directory}</outputDirectory>
+ <overWriteReleases>false</overWriteReleases>
+ <overWriteSnapshots>true</overWriteSnapshots>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <executions>
+ <execution>
+ <!-- disable annotation processing for first pass -->
+ <id>generate-plugins</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ <configuration>
+ <excludes>
+ <exclude>module-info.java</exclude>
+ </excludes>
+ </configuration>
+ </execution>
+ <execution>
+ <!-- disable annotation processing for first pass -->
+ <id>generate-test-plugins</id>
+ <phase>generate-test-sources</phase>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ <configuration>
+ <excludes>
+ <exclude>module-info.java</exclude>
+ </excludes>
+ <proc>only</proc>
+ </configuration>
+ </execution>
+ <execution>
+ <!-- disable annotation processing for first pass -->
+ <id>default-compile</id>
+ <configuration>
+ <excludes>
+ <exclude>module-info.java</exclude>
+ </excludes>
+ <proc>none</proc>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <configuration>
+ <excludedGroups>
+ org.apache.logging.log4j.categories.PerformanceTests
+ </excludedGroups>
+ <systemPropertyVariables>
+ <org.apache.activemq.SERIALIZABLE_PACKAGES>*</org.apache.activemq.SERIALIZABLE_PACKAGES>
+ </systemPropertyVariables>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-failsafe-plugin</artifactId>
+ <configuration>
+ <skipTests>true</skipTests>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jar-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>default-jar</id>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ <configuration combine.self="override">
+ <archive>
+ <manifestFile>${manifestfile}</manifestFile>
+ <manifestEntries>
+ <Specification-Title>${project.name}</Specification-Title>
+ <Specification-Version>${project.version}</Specification-Version>
+ <Specification-Vendor>${project.organization.name}</Specification-Vendor>
+ <Implementation-Title>${project.name}</Implementation-Title>
+ <Implementation-Version>${project.version}</Implementation-Version>
+ <Implementation-Vendor>${project.organization.name}</Implementation-Vendor>
+ <Implementation-Vendor-Id>org.apache</Implementation-Vendor-Id>
+ <X-Compile-Source-JDK>${maven.compiler.source}</X-Compile-Source-JDK>
+ <X-Compile-Target-JDK>${maven.compiler.target}</X-Compile-Target-JDK>
+ <Automatic-Module-Name>org.apache.logging.log4j.plugins</Automatic-Module-Name>
+ <Multi-Release>true</Multi-Release>
+ </manifestEntries>
+ </archive>
+ </configuration>
+ </execution>
+ <execution>
+ <id>default</id>
+ <goals>
+ <goal>test-jar</goal>
+ </goals>
+ <configuration>
+ <archive>
+ <manifestFile>${manifestfile}</manifestFile>
+ <manifestEntries>
+ <Specification-Title>${project.name}</Specification-Title>
+ <Specification-Version>${project.version}</Specification-Version>
+ <Specification-Vendor>${project.organization.name}</Specification-Vendor>
+ <Implementation-Title>${project.name}</Implementation-Title>
+ <Implementation-Version>${project.version}</Implementation-Version>
+ <Implementation-Vendor>${project.organization.name}</Implementation-Vendor>
+ <Implementation-Vendor-Id>org.apache</Implementation-Vendor-Id>
+ <X-Compile-Source-JDK>${maven.compiler.source}</X-Compile-Source-JDK>
+ <X-Compile-Target-JDK>${maven.compiler.target}</X-Compile-Target-JDK>
+ </manifestEntries>
+ </archive>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <configuration>
+ <instructions>
+ <Bundle-SymbolicName>org.apache.logging.log4j.plugins</Bundle-SymbolicName>
+ <!-- TODO: exclude internal classes from export -->
+ <Export-Package>org.apache.logging.log4j.plugins.*</Export-Package>
+ <Import-Package>
+ sun.reflect;resolution:=optional,
+ org.apache.logging.log4j.util,
+ *
+ </Import-Package>
+ <Bundle-Activator>org.apache.logging.log4j.plugins.osgi.Activator</Bundle-Activator>
+ </instructions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+ <reporting>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-changes-plugin</artifactId>
+ <version>${changes.plugin.version}</version>
+ <reportSets>
+ <reportSet>
+ <reports>
+ <report>changes-report</report>
+ </reports>
+ </reportSet>
+ </reportSets>
+ <configuration>
+ <issueLinkTemplate>%URL%/show_bug.cgi?id=%ISSUE%</issueLinkTemplate>
+ <useJql>true</useJql>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-checkstyle-plugin</artifactId>
+ <version>${checkstyle.plugin.version}</version>
+ <configuration>
+ <!--<propertiesLocation>${vfs.parent.dir}/checkstyle.properties</propertiesLocation> -->
+ <configLocation>${log4jParentDir}/checkstyle.xml</configLocation>
+ <suppressionsLocation>${log4jParentDir}/checkstyle-suppressions.xml</suppressionsLocation>
+ <enableRulesSummary>false</enableRulesSummary>
+ <propertyExpansion>basedir=${basedir}</propertyExpansion>
+ <propertyExpansion>licensedir=${log4jParentDir}/checkstyle-header.txt</propertyExpansion>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ <version>${javadoc.plugin.version}</version>
+ <configuration>
+ <failOnError>false</failOnError>
+ <bottom><![CDATA[<p align="center">Copyright © {inceptionYear}-{currentYear} {organizationName}. All Rights Reserved.<br />
+ Apache Logging, Apache Log4j, Log4j, Apache, the Apache feather logo, the Apache Logging project logo,
+ and the Apache Log4j logo are trademarks of The Apache Software Foundation.</p>]]></bottom>
+ <!-- module link generation is completely broken in the javadoc plugin for a multi-module non-aggregating
+ project -->
+ <additionalparam>${javadoc.opts}</additionalparam>
+ <detectOfflineLinks>false</detectOfflineLinks>
+ <linksource>true</linksource>
+ <links>
+ <link>http://docs.oracle.com/javaee/6/api/</link>
+ <link>http://www.osgi.org/javadoc/r4v43/core/</link>
+ <link>https://commons.apache.org/proper/commons-lang/javadocs/api-release/</link>
+ </links>
+ <groups>
+ <group>
+ <title>Core API</title>
+ <packages>org.apache.logging.log4j.core</packages>
+ </group>
+ <group>
+ <title>Configuration</title>
+ <packages>org.apache.logging.log4j.core.config*:org.apache.logging.log4j.core.selector</packages>
+ </group>
+ <group>
+ <title>Core Plugins</title>
+ <packages>org.apache.logging.log4j.core.appender*:org.apache.logging.log4j.core.filter:org.apache.logging.log4j.core.layout:org.apache.logging.log4j.core.lookup:org.apache.logging.log4j.core.pattern:org.apache.logging.log4j.core.script</packages>
+ </group>
+ <group>
+ <title>Tools</title>
+ <packages>org.apache.logging.log4j.core.net*:org.apache.logging.log4j.core.tools</packages>
+ </group>
+ <group>
+ <title>Internals</title>
+ <packages>org.apache.logging.log4j.core.async:org.apache.logging.log4j.core.impl:org.apache.logging.log4j.core.util*:org.apache.logging.log4j.core.osgi:org.apache.logging.log4j.core.jackson:org.apache.logging.log4j.core.jmx</packages>
+ </group>
+ </groups>
+ </configuration>
+ <reportSets>
+ <reportSet>
+ <id>non-aggregate</id>
+ <reports>
+ <report>javadoc</report>
+ </reports>
+ </reportSet>
+ </reportSets>
+ </plugin>
+ <plugin>
+ <groupId>com.github.spotbugs</groupId>
+ <artifactId>spotbugs-maven-plugin</artifactId>
+ <configuration>
+ <fork>true</fork>
+ <jvmArgs>-Duser.language=en</jvmArgs>
+ <threshold>Normal</threshold>
+ <effort>Default</effort>
+ <excludeFilterFile>${log4jParentDir}/spotbugs-exclude-filter.xml</excludeFilterFile>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jxr-plugin</artifactId>
+ <version>${jxr.plugin.version}</version>
+ <reportSets>
+ <reportSet>
+ <id>non-aggregate</id>
+ <reports>
+ <report>jxr</report>
+ </reports>
+ </reportSet>
+ <reportSet>
+ <id>aggregate</id>
+ <reports>
+ <report>aggregate</report>
+ </reports>
+ </reportSet>
+ </reportSets>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-pmd-plugin</artifactId>
+ <version>${pmd.plugin.version}</version>
+ <configuration>
+ <targetJdk>${maven.compiler.target}</targetJdk>
+ </configuration>
+ </plugin>
+ </plugins>
+ </reporting>
+</project>
+
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/Node.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Node.java
similarity index 97%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/Node.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Node.java
index c92c904..22fd9bf 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/Node.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Node.java
@@ -14,15 +14,15 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.util.PluginType;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
-import org.apache.logging.log4j.core.config.plugins.util.PluginType;
-
/**
* A Configuration node.
*/
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/Plugin.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Plugin.java
similarity index 97%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/Plugin.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Plugin.java
index 8aaf117..348754f 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/Plugin.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/Plugin.java
@@ -14,7 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.util.Strings;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -22,8 +24,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.util.Strings;
-
/**
* Annotation that identifies a Class as a Plugin.
*/
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAliases.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAliases.java
similarity index 87%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAliases.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAliases.java
index 7be3dea..4dce103 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAliases.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAliases.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -23,7 +23,7 @@ import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
- * Identifies a list of aliases for a {@link Plugin}, {@link PluginAttribute}, or {@link PluginBuilderAttribute}.
+ * Identifies a list of aliases for a Plugin, PluginAttribute, or PluginBuilderAttribute.
*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAttribute.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAttribute.java
similarity index 96%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAttribute.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAttribute.java
index bd88220..b9d4684 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginAttribute.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginAttribute.java
@@ -14,7 +14,10 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginAttributeVisitor;
+import org.apache.logging.log4j.util.Strings;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -22,9 +25,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginAttributeVisitor;
-import org.apache.logging.log4j.util.Strings;
-
/**
* Identifies a Plugin Attribute and its default value. Note that only one of the defaultFoo attributes will be
* used based on the type this annotation is attached to. Thus, for primitive types, the default<i>Type</i>
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderAttribute.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderAttribute.java
similarity index 92%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderAttribute.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderAttribute.java
index 675d78f..c7fce2f 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderAttribute.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderAttribute.java
@@ -15,7 +15,10 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginBuilderAttributeVisitor;
+import org.apache.logging.log4j.util.Strings;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -23,9 +26,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginBuilderAttributeVisitor;
-import org.apache.logging.log4j.util.Strings;
-
/**
* Marks a field as a Plugin Attribute.
*/
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderFactory.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderFactory.java
similarity index 95%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderFactory.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderFactory.java
index 4e69262..035b025 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginBuilderFactory.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginBuilderFactory.java
@@ -15,7 +15,7 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginElement.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginElement.java
similarity index 91%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginElement.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginElement.java
index 7ea358b..6cfb6fa 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginElement.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginElement.java
@@ -14,7 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginElementVisitor;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -22,8 +24,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginElementVisitor;
-
/**
* Identifies a parameter as a Plugin and corresponds with an XML element (or equivalent) in configuration files.
*/
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginFactory.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginFactory.java
similarity index 96%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginFactory.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginFactory.java
index 1c04106..b071510 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginFactory.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginFactory.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginNode.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginNode.java
similarity index 90%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginNode.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginNode.java
index d60f1b5..b172268 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginNode.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginNode.java
@@ -14,7 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginNodeVisitor;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -22,8 +24,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginNodeVisitor;
-
/**
* Identifies a Plugin configuration Node.
*/
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginValue.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginValue.java
similarity index 91%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginValue.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginValue.java
index 9c20cc2..31e5a23 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginValue.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginValue.java
@@ -14,7 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginValueVisitor;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
@@ -22,8 +24,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginValueVisitor;
-
/**
* Identifies a parameter as a value. These correspond with property values generally, but are meant as values to be
* used as a placeholder value somewhere.
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginVisitorStrategy.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginVisitorStrategy.java
similarity index 89%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginVisitorStrategy.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginVisitorStrategy.java
index 65fcb76..093cc50 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/PluginVisitorStrategy.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/PluginVisitorStrategy.java
@@ -15,7 +15,9 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins;
+package org.apache.logging.log4j.plugins;
+
+import org.apache.logging.log4j.plugins.visitors.PluginVisitor;
import java.lang.annotation.Annotation;
import java.lang.annotation.Documented;
@@ -24,8 +26,6 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import org.apache.logging.log4j.core.config.plugins.visitors.PluginVisitor;
-
/**
* Meta-annotation to denote the class name to use that implements
* {@link org.apache.logging.log4j.core.config.plugins.visitors.PluginVisitor} for the annotated annotation.
@@ -40,5 +40,5 @@ public @interface PluginVisitorStrategy {
* for the given annotation. The generic type in {@code PluginVisitor} should match the annotation this annotation
* is applied to.
*/
- Class<? extends PluginVisitor<? extends Annotation>> value();
+ Class<? extends PluginVisitor<? extends Annotation, ?>> value();
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/EnumConverter.java
similarity index 95%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/EnumConverter.java
index 15a162c..fd8012a 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/EnumConverter.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
import org.apache.logging.log4j.util.EnglishEnums;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/HexConverter.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/HexConverter.java
similarity index 95%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/HexConverter.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/HexConverter.java
index e629657..f9037b3 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/HexConverter.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/HexConverter.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
/**
* Converts Strings to hex. This is used in place of java.xml.bind.DataTypeConverter which is not available by
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverter.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverter.java
similarity index 95%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverter.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverter.java
index e67e213..aaa5b4d 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverter.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverter.java
@@ -15,7 +15,7 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
/**
* Interface for doing automatic String conversion to a specific type.
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistry.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistry.java
similarity index 92%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistry.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistry.java
index 5088f15..fb5b27e 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistry.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistry.java
@@ -14,7 +14,14 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
+
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.plugins.util.PluginManager;
+import org.apache.logging.log4j.plugins.util.PluginType;
+import org.apache.logging.log4j.plugins.util.TypeUtil;
+import org.apache.logging.log4j.util.ReflectionUtil;
+import org.apache.logging.log4j.status.StatusLogger;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
@@ -25,13 +32,6 @@ import java.util.UnknownFormatConversionException;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.util.PluginManager;
-import org.apache.logging.log4j.core.config.plugins.util.PluginType;
-import org.apache.logging.log4j.core.util.ReflectionUtil;
-import org.apache.logging.log4j.core.util.TypeUtil;
-import org.apache.logging.log4j.status.StatusLogger;
-
/**
* Registry for {@link TypeConverter} plugins.
*
@@ -152,7 +152,12 @@ public class TypeConverterRegistry {
}
private void registerTypeAlias(final Type knownType, final Type aliasType) {
- registry.putIfAbsent(aliasType, registry.get(knownType));
+ TypeConverter<?> converter = registry.get(knownType);
+ if (converter != null) {
+ registry.putIfAbsent(aliasType, converter);
+ } else {
+ LOGGER.error("Cannot locate converter for {}", knownType);
+ }
}
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverters.java
similarity index 92%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverters.java
index dc833f0..7a71b4a 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverters.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/TypeConverters.java
@@ -15,32 +15,27 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
+
+import org.apache.logging.log4j.Level;
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.status.StatusLogger;
+import org.apache.logging.log4j.util.LoaderUtil;
import java.io.File;
import java.math.BigDecimal;
import java.math.BigInteger;
-import java.net.InetAddress;
-import java.net.MalformedURLException;
-import java.net.URI;
-import java.net.URISyntaxException;
-import java.net.URL;
+import java.net.*;
import java.nio.charset.Charset;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.security.Provider;
import java.security.Security;
+import java.util.Base64;
import java.util.UUID;
import java.util.regex.Pattern;
-import org.apache.logging.log4j.Level;
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.appender.rolling.action.Duration;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.util.CronExpression;
-import org.apache.logging.log4j.status.StatusLogger;
-import org.apache.logging.log4j.util.LoaderUtil;
-
/**
* Collection of basic TypeConverter implementations. May be used to register additional TypeConverters or find
* registered TypeConverters.
@@ -56,6 +51,8 @@ public final class TypeConverters {
*/
public static final String CATEGORY = "TypeConverter";
+ private static final Base64.Decoder decoder = Base64.getDecoder();
+
/**
* Parses a {@link String} into a {@link BigDecimal}.
*/
@@ -112,7 +109,7 @@ public final class TypeConverters {
bytes = new byte[0];
} else if (value.startsWith(PREFIX_BASE64)) {
final String lexicalXSDBase64Binary = value.substring(PREFIX_BASE64.length());
- bytes = Base64Converter.parseBase64Binary(lexicalXSDBase64Binary);
+ bytes = decoder.decode(lexicalXSDBase64Binary);
} else if (value.startsWith(PREFIX_0x)) {
final String lexicalXSDHexBinary = value.substring(PREFIX_0x.length());
bytes = HexConverter.parseHexBinary(lexicalXSDHexBinary);
@@ -203,14 +200,6 @@ public final class TypeConverters {
}
}
- @Plugin(name = "CronExpression", category = CATEGORY)
- public static class CronExpressionConverter implements TypeConverter<CronExpression> {
- @Override
- public CronExpression convert(final String s) throws Exception {
- return new CronExpression(s);
- }
- }
-
/**
* Converts a {@link String} into a {@link Double}.
*/
@@ -223,18 +212,6 @@ public final class TypeConverters {
}
/**
- * Converts a {@link String} into a {@link Duration}.
- * @since 2.5
- */
- @Plugin(name = "Duration", category = CATEGORY)
- public static class DurationConverter implements TypeConverter<Duration> {
- @Override
- public Duration convert(final String s) {
- return Duration.parse(s);
- }
- }
-
- /**
* Converts a {@link String} into a {@link File}.
*/
@Plugin(name = "File", category = CATEGORY)
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/package-info.java
similarity index 80%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/package-info.java
index f22ba49..958beb4 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/convert/package-info.java
@@ -16,8 +16,7 @@
*/
/**
- * Validation annotations.
- *
- * @since 2.1
+ * TypeConverter plugins for converter strings into various types. These plugins are used for parsing plugin
+ * attributes in plugin factory methods.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.convert;
diff --git a/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/Activator.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/Activator.java
new file mode 100644
index 0000000..518bee7
--- /dev/null
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/Activator.java
@@ -0,0 +1,103 @@
+/*
+ * 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.plugins.osgi;
+
+import org.apache.logging.log4j.LogManager;
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.plugins.processor.PluginService;
+import org.apache.logging.log4j.plugins.util.PluginRegistry;
+import org.apache.logging.log4j.spi.Provider;
+import org.apache.logging.log4j.status.StatusLogger;
+import org.apache.logging.log4j.util.PropertiesUtil;
+import org.osgi.framework.*;
+import org.osgi.framework.wiring.BundleWiring;
+
+import java.util.Hashtable;
+import java.util.concurrent.atomic.AtomicReference;
+
+/**
+ * OSGi BundleActivator.
+ */
+public final class Activator implements BundleActivator, SynchronousBundleListener {
+
+ private static final Logger LOGGER = StatusLogger.getLogger();
+
+ private final AtomicReference<BundleContext> contextRef = new AtomicReference<>();
+
+ ServiceRegistration provideRegistration = null;
+
+ @Override
+ public void start(final BundleContext context) throws Exception {
+ final PluginService pluginService = new Log4jProvider();
+ final Hashtable<String, String> props = new Hashtable<>();
+ props.put("APIVersion", "3.0");
+ provideRegistration = context.registerService(pluginService.class.getName(), provider, props);
+ if (this.contextRef.compareAndSet(null, context)) {
+ context.addBundleListener(this);
+ // done after the BundleListener as to not miss any new bundle installs in the interim
+ scanInstalledBundlesForPlugins(context);
+ }
+ }
+
+ private static void scanInstalledBundlesForPlugins(final BundleContext context) {
+ final Bundle[] bundles = context.getBundles();
+ for (final Bundle bundle : bundles) {
+ // TODO: bundle state can change during this
+ scanBundleForPlugins(bundle);
+ }
+ }
+
+ private static void scanBundleForPlugins(final Bundle bundle) {
+ final long bundleId = bundle.getBundleId();
+ // LOG4J2-920: don't scan system bundle for plugins
+ if (bundle.getState() == Bundle.ACTIVE && bundleId != 0) {
+ LOGGER.trace("Scanning bundle [{}, id=%d] for plugins.", bundle.getSymbolicName(), bundleId);
+ PluginRegistry.getInstance().loadFromBundle(bundleId,
+ bundle.adapt(BundleWiring.class).getClassLoader());
+ }
+ }
+
+ private static void stopBundlePlugins(final Bundle bundle) {
+ LOGGER.trace("Stopping bundle [{}] plugins.", bundle.getSymbolicName());
+ // TODO: plugin lifecycle code
+ PluginRegistry.getInstance().clearBundlePlugins(bundle.getBundleId());
+ }
+
+ @Override
+ public void stop(final BundleContext context) throws Exception {
+ provideRegistration.unregister();
+ this.contextRef.compareAndSet(context, null);
+ }
+
+ @Override
+ public void bundleChanged(final BundleEvent event) {
+ switch (event.getType()) {
+ // FIXME: STARTING instead of STARTED?
+ case BundleEvent.STARTED:
+ scanBundleForPlugins(event.getBundle());
+ break;
+
+ case BundleEvent.STOPPING:
+ stopBundlePlugins(event.getBundle());
+ break;
+
+ default:
+ break;
+ }
+ }
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/package-info.java
similarity index 87%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/package-info.java
index f22ba49..37dadd4 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/osgi/package-info.java
@@ -16,8 +16,6 @@
*/
/**
- * Validation annotations.
- *
- * @since 2.1
+ * Collection of OSGi-specific classes for bundles.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.osgi;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/package-info.java
similarity index 87%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/package-info.java
index f22ba49..b161185 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/package-info.java
@@ -16,8 +16,6 @@
*/
/**
- * Validation annotations.
- *
- * @since 2.1
+ * Annotations for Log4j 2 plugins.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginCache.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginCache.java
similarity index 71%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginCache.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginCache.java
index 2fd4160..784dece 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginCache.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginCache.java
@@ -15,7 +15,7 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
@@ -60,34 +60,6 @@ public class PluginCache {
}
/**
- * Stores the plugin cache to a given OutputStream.
- *
- * @param os destination to save cache to.
- * @throws IOException if an I/O exception occurs.
- */
- // NOTE: if this file format is to be changed, the filename should change and this format should still be readable
- public void writeCache(final OutputStream os) throws IOException {
- try (final DataOutputStream out = new DataOutputStream(new BufferedOutputStream(os))) {
- // See PluginManager.readFromCacheFiles for the corresponding decoder. Format may not be changed
- // without breaking existing Log4j2Plugins.dat files.
- out.writeInt(categories.size());
- for (final Map.Entry<String, Map<String, PluginEntry>> category : categories.entrySet()) {
- out.writeUTF(category.getKey());
- final Map<String, PluginEntry> m = category.getValue();
- out.writeInt(m.size());
- for (final Map.Entry<String, PluginEntry> entry : m.entrySet()) {
- final PluginEntry plugin = entry.getValue();
- out.writeUTF(plugin.getKey());
- out.writeUTF(plugin.getClassName());
- out.writeUTF(plugin.getName());
- out.writeBoolean(plugin.isPrintable());
- out.writeBoolean(plugin.isDefer());
- }
- }
- }
- }
-
- /**
* Loads and merges all the Log4j plugin cache files specified. Usually, this is obtained via a ClassLoader.
*
* @param resources URLs to all the desired plugin cache files to load.
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginEntry.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginEntry.java
similarity index 85%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginEntry.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginEntry.java
index dd43601..bd452d3 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginEntry.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginEntry.java
@@ -15,7 +15,7 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
import java.io.Serializable;
@@ -32,6 +32,18 @@ public class PluginEntry implements Serializable {
private boolean defer;
private transient String category;
+ public PluginEntry() {
+ }
+
+ public PluginEntry(String key, String className, String name, boolean printable, boolean defer, String category) {
+ this.key = key;
+ this.className = className;
+ this.name = name;
+ this.printable = printable;
+ this.defer = defer;
+ this.category = category;
+ }
+
public String getKey() {
return key;
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginProcessor.java
similarity index 54%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginProcessor.java
index 2f3b53f..975d2ab 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginProcessor.java
@@ -15,38 +15,47 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
+
+import org.apache.logging.log4j.LoggingException;
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.plugins.PluginAliases;
+import org.apache.logging.log4j.util.Strings;
-import java.io.IOException;
-import java.io.OutputStream;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Objects;
-import java.util.Set;
import javax.annotation.processing.AbstractProcessor;
+import javax.annotation.processing.Messager;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.SupportedAnnotationTypes;
import javax.lang.model.SourceVersion;
import javax.lang.model.element.Element;
import javax.lang.model.element.ElementVisitor;
+import javax.lang.model.element.Name;
import javax.lang.model.element.TypeElement;
import javax.lang.model.util.Elements;
import javax.lang.model.util.SimpleElementVisitor7;
import javax.tools.Diagnostic.Kind;
import javax.tools.FileObject;
+import javax.tools.JavaFileObject;
import javax.tools.StandardLocation;
+import java.io.BufferedWriter;
+import java.io.IOException;
+import java.io.OutputStreamWriter;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginAliases;
-import org.apache.logging.log4j.util.Strings;
+import static java.nio.charset.StandardCharsets.UTF_8;
/**
* Annotation processor for pre-scanning Log4j 2 plugins.
*/
-@SupportedAnnotationTypes("org.apache.logging.log4j.core.config.plugins.*")
+@SupportedAnnotationTypes({"org.apache.logging.log4j.plugins.*", "org.apache.logging.log4j.core.config.plugins.*"})
public class PluginProcessor extends AbstractProcessor {
// TODO: this could be made more abstract to allow for compile-time and run-time plugin processing
@@ -57,8 +66,8 @@ public class PluginProcessor extends AbstractProcessor {
*/
public static final String PLUGIN_CACHE_FILE =
"META-INF/org/apache/logging/log4j/core/config/plugins/Log4j2Plugins.dat";
-
- private final PluginCache pluginCache = new PluginCache();
+ private static final String SERVICE_FILE_NAME =
+ "META-INF/services/org.apache.logging.log4j.plugins.processor.PluginService";
@Override
public SourceVersion getSupportedSourceVersion() {
@@ -67,16 +76,21 @@ public class PluginProcessor extends AbstractProcessor {
@Override
public boolean process(final Set<? extends TypeElement> annotations, final RoundEnvironment roundEnv) {
- System.out.println("Processing annotations");
+ Map<String, String> options = processingEnv.getOptions();
+ String packageName = options.get("pluginPackage");
+ Messager messager = processingEnv.getMessager();
+ messager.printMessage(Kind.NOTE, "Processing Log4j annotations");
try {
final Set<? extends Element> elements = roundEnv.getElementsAnnotatedWith(Plugin.class);
if (elements.isEmpty()) {
- System.out.println("No elements to process");
+ messager.printMessage(Kind.NOTE, "No elements to process");
return false;
}
- collectPlugins(elements);
- writeCacheFile(elements.toArray(new Element[elements.size()]));
- System.out.println("Annotations processed");
+ List<PluginEntry> list = new ArrayList<>();
+ packageName = collectPlugins(packageName, elements, list);
+ writeClassFile(packageName, list);
+ writeServiceFile(packageName);
+ messager.printMessage(Kind.NOTE, "Annotations processed");
return true;
} catch (final IOException e) {
e.printStackTrace();
@@ -93,7 +107,8 @@ public class PluginProcessor extends AbstractProcessor {
processingEnv.getMessager().printMessage(Kind.ERROR, message);
}
- private void collectPlugins(final Iterable<? extends Element> elements) {
+ private String collectPlugins(String packageName, final Iterable<? extends Element> elements, List<PluginEntry> list) {
+ boolean calculatePackage = packageName == null;
final Elements elementUtils = processingEnv.getElementUtils();
final ElementVisitor<PluginEntry, Plugin> pluginVisitor = new PluginElementVisitor(elementUtils);
final ElementVisitor<Collection<PluginEntry>, Plugin> pluginAliasesVisitor = new PluginAliasesElementVisitor(
@@ -104,23 +119,93 @@ public class PluginProcessor extends AbstractProcessor {
continue;
}
final PluginEntry entry = element.accept(pluginVisitor, plugin);
- final Map<String, PluginEntry> category = pluginCache.getCategory(entry.getCategory());
- category.put(entry.getKey(), entry);
+ list.add(entry);
+ if (calculatePackage) {
+ packageName = calculatePackage(elementUtils, element, packageName);
+ }
final Collection<PluginEntry> entries = element.accept(pluginAliasesVisitor, plugin);
for (final PluginEntry pluginEntry : entries) {
- category.put(pluginEntry.getKey(), pluginEntry);
+ list.add(pluginEntry);
}
}
+ return packageName;
}
- private void writeCacheFile(final Element... elements) throws IOException {
+ private String calculatePackage(Elements elements, Element element, String packageName) {
+ Name name = elements.getPackageOf(element).getQualifiedName();
+ if (name == null) {
+ return null;
+ }
+ String pkgName = name.toString();
+ if (packageName == null) {
+ return pkgName;
+ }
+ if (pkgName.length() == packageName.length()) {
+ return packageName;
+ }
+ if (pkgName.length() < packageName.length() && packageName.startsWith(pkgName)) {
+ return pkgName;
+ }
+
+ return commonPrefix(pkgName, packageName);
+ }
+
+ private void writeServiceFile(String pkgName) throws IOException {
final FileObject fileObject = processingEnv.getFiler().createResource(StandardLocation.CLASS_OUTPUT, Strings.EMPTY,
- PLUGIN_CACHE_FILE, elements);
- try (final OutputStream out = fileObject.openOutputStream()) {
- pluginCache.writeCache(out);
+ SERVICE_FILE_NAME);
+ try (final PrintWriter writer = new PrintWriter(new BufferedWriter(new OutputStreamWriter(fileObject.openOutputStream(), UTF_8)))) {
+ writer.println(createFqcn(pkgName));
+ }
+ }
+
+ private void writeClassFile(String pkg, List<PluginEntry> list) {
+ String fqcn = createFqcn(pkg);
+ try (final PrintWriter writer = createSourceFile(fqcn)) {
+ writer.println("package " + pkg + ".plugins;");
+ writer.println("");
+ writer.println("import org.apache.logging.log4j.plugins.processor.PluginEntry;");
+ writer.println("import org.apache.logging.log4j.plugins.processor.PluginService;");
+ writer.println("");
+ writer.println("public class Log4jPlugins extends PluginService {");
+ writer.println("");
+ writer.println(" private static PluginEntry[] entries = new PluginEntry[] {");
+ StringBuilder sb = new StringBuilder();
+ int max = list.size() - 1;
+ for (int i = 0; i < list.size(); ++i) {
+ PluginEntry entry = list.get(i);
+ sb.append(" ").append("new PluginEntry(\"");
+ sb.append(entry.getKey()).append("\", \"");
+ sb.append(entry.getClassName()).append("\", \"");
+ sb.append(entry.getName()).append("\", ");
+ sb.append(entry.isPrintable()).append(", ");
+ sb.append(entry.isDefer()).append(", \"");
+ sb.append(entry.getCategory()).append("\")");
+ if (i < max) {
+ sb.append(",");
+ }
+ writer.println(sb.toString());
+ sb.setLength(0);
+ }
+ writer.println(" };");
+ writer.println(" @Override");
+ writer.println(" public PluginEntry[] getEntries() { return entries;}");
+ writer.println("}");
}
}
+ private PrintWriter createSourceFile(String fqcn) {
+ try {
+ JavaFileObject sourceFile = processingEnv.getFiler().createSourceFile(fqcn);
+ return new PrintWriter(sourceFile.openWriter());
+ } catch (IOException e) {
+ throw new LoggingException("Unable to create Plugin Service Class " + fqcn, e);
+ }
+ }
+
+ private String createFqcn(String packageName) {
+ return packageName + ".plugins.Log4jPlugins";
+ }
+
/**
* ElementVisitor to scan the Plugin annotation.
*/
@@ -146,6 +231,20 @@ public class PluginProcessor extends AbstractProcessor {
}
}
+ private String commonPrefix(String str1, String str2) {
+ int minLength = str1.length() < str2.length() ? str1.length() : str2.length();
+ for (int i = 0; i < minLength; i++) {
+ if (str1.charAt(i) != str2.charAt(i)) {
+ if (i > 1 && str1.charAt(i-1) == '.') {
+ return str1.substring(0, i-1);
+ } else {
+ return str1.substring(0, i);
+ }
+ }
+ }
+ return str1.substring(0, minLength);
+ }
+
/**
* ElementVisitor to scan the PluginAliases annotation.
*/
diff --git a/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java
new file mode 100644
index 0000000..5042456
--- /dev/null
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/PluginService.java
@@ -0,0 +1,56 @@
+/*
+ * 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.plugins.processor;
+
+import java.util.Collections;
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+/**
+ * Class Description goes here.
+ */
+public abstract class PluginService {
+
+ private final Map<String, Map<String, PluginEntry>> categories = new LinkedHashMap<>();
+
+ public PluginService() {
+ PluginEntry[] entries = getEntries();
+ for (PluginEntry entry : entries) {
+ String category = entry.getCategory().toLowerCase();
+ if (!categories.containsKey(category)) {
+ categories.put(category, new LinkedHashMap<>());
+ }
+ Map<String, PluginEntry> map = categories.get(category);
+ map.put(entry.getKey(), entry);
+ }
+ }
+
+ public abstract PluginEntry[] getEntries();
+
+ public Map<String, Map<String, PluginEntry>> getCategories() {
+ return Collections.unmodifiableMap(categories);
+ }
+
+ public Map<String, PluginEntry> getCategory(String category) {
+ return Collections.unmodifiableMap(categories.get(category.toLowerCase()));
+ }
+
+ public long size() {
+ return categories.size();
+ }
+
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/package-info.java
similarity index 94%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/package-info.java
index 4f6ddda..2c296f9 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/processor/package-info.java
@@ -19,4 +19,4 @@
* Java annotation processor for pre-scanning Log4j 2 plugins. This is provided as an alternative to using the
* executable {@link org.apache.logging.log4j.core.config.plugins.util.PluginManager} class in your build process.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/Builder.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/Builder.java
similarity index 93%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/util/Builder.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/Builder.java
index 0935ce8..ec8a07f 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/util/Builder.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/Builder.java
@@ -15,7 +15,7 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.util;
+package org.apache.logging.log4j.plugins.util;
/**
* A type of builder that can be used to configure and create a instances using a Java DSL instead of
@@ -25,7 +25,7 @@ package org.apache.logging.log4j.core.util;
* <p>
* When creating <em>plugin</em> builders, it is customary to create the builder class as a public static inner class
* called {@code Builder}. For instance, the builder class for
- * {@link org.apache.logging.log4j.core.layout.PatternLayout PatternLayout} would be
+ * org.apache.logging.log4j.core.layout.PatternLayout PatternLayout would be
* {@code PatternLayout.Builder}.
* </p>
*
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginManager.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginManager.java
similarity index 96%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginManager.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginManager.java
index 6f38d0e..b6f02f5 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginManager.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginManager.java
@@ -15,17 +15,13 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.status.StatusLogger;
import org.apache.logging.log4j.util.Strings;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.LinkedHashMap;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
import java.util.concurrent.CopyOnWriteArrayList;
/**
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginRegistry.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginRegistry.java
similarity index 81%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginRegistry.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginRegistry.java
index 99fa610..9e8c6e2 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginRegistry.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginRegistry.java
@@ -15,32 +15,28 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
+
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.plugins.PluginAliases;
+import org.apache.logging.log4j.plugins.processor.PluginCache;
+import org.apache.logging.log4j.plugins.processor.PluginEntry;
+import org.apache.logging.log4j.plugins.processor.PluginProcessor;
+import org.apache.logging.log4j.plugins.processor.PluginService;
+import org.apache.logging.log4j.status.StatusLogger;
+import org.apache.logging.log4j.util.LoaderUtil;
+import org.apache.logging.log4j.util.Strings;
import java.io.IOException;
import java.net.URI;
import java.net.URL;
import java.text.DecimalFormat;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.atomic.AtomicReference;
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginAliases;
-import org.apache.logging.log4j.core.config.plugins.processor.PluginCache;
-import org.apache.logging.log4j.core.config.plugins.processor.PluginEntry;
-import org.apache.logging.log4j.core.config.plugins.processor.PluginProcessor;
-import org.apache.logging.log4j.core.util.Loader;
-import org.apache.logging.log4j.status.StatusLogger;
-import org.apache.logging.log4j.util.Strings;
-
/**
* Registry singleton for PluginType maps partitioned by source type and then by category names.
*/
@@ -116,7 +112,8 @@ public class PluginRegistry {
// already loaded
return existing;
}
- final Map<String, List<PluginType<?>>> newPluginsByCategory = decodeCacheFiles(Loader.getClassLoader());
+ final Map<String, List<PluginType<?>>> newPluginsByCategory = decodeCacheFiles(LoaderUtil.getClassLoader());
+ loadPlugins(newPluginsByCategory);
// Note multiple threads could be calling this method concurrently. Both will do the work,
// but only one will be allowed to store the result in the AtomicReference.
@@ -144,6 +141,7 @@ public class PluginRegistry {
return existing;
}
final Map<String, List<PluginType<?>>> newPluginsByCategory = decodeCacheFiles(loader);
+ loadPlugins(loader, newPluginsByCategory);
// Note multiple threads could be calling this method concurrently. Both will do the work,
// but only one will be allowed to store the result in the outer map.
@@ -155,6 +153,51 @@ public class PluginRegistry {
return newPluginsByCategory;
}
+ /**
+ * @since 3.0
+ */
+ public void loadPlugins(Map<String, List<PluginType<?>>> map) {
+ for (ClassLoader classLoader : LoaderUtil.getClassLoaders()) {
+ try {
+ loadPlugins(classLoader, map);
+ } catch (Throwable ex) {
+ LOGGER.debug("Unable to retrieve provider from ClassLoader {}", classLoader, ex);
+ }
+ }
+ }
+
+ /**
+ * @since 3.0
+ */
+ public void loadPlugins(ClassLoader classLoader, Map<String, List<PluginType<?>>> map) {
+ final long startTime = System.nanoTime();
+ final ServiceLoader<PluginService> serviceLoader = ServiceLoader.load(PluginService.class, classLoader);
+ int pluginCount = 0;
+ for (final PluginService pluginService : serviceLoader) {
+ PluginEntry[] entries = pluginService.getEntries();
+ for (PluginEntry entry : entries) {
+ try {
+ final Class<?> clazz = classLoader.loadClass(entry.getClassName());
+ final PluginType<?> type = new PluginType(entry, clazz, entry.getName());
+ String category = entry.getCategory().toLowerCase();
+ if (!map.containsKey(category)) {
+ map.put(category, new ArrayList<>());
+ }
+ List<PluginType<?>> list = map.get(category);
+ list.add(type);
+ ++pluginCount;
+ } catch (final ClassNotFoundException e) {
+ LOGGER.info("Plugin [{}] could not be loaded due to missing classes.", entry.getClassName(), e);
+ }
+ }
+ }
+ final long endTime = System.nanoTime();
+ final DecimalFormat numFormat = new DecimalFormat("#0.000000");
+ final double seconds = (endTime - startTime) * 1e-9;
+ LOGGER.debug("Took {} seconds to load {} plugins from {}",
+ numFormat.format(seconds), pluginCount, classLoader);
+ }
+
private Map<String, List<PluginType<?>>> decodeCacheFiles(final ClassLoader loader) {
final long startTime = System.nanoTime();
final PluginCache cache = new PluginCache();
@@ -214,7 +257,7 @@ public class PluginRegistry {
final long startTime = System.nanoTime();
final ResolverUtil resolver = new ResolverUtil();
- final ClassLoader classLoader = Loader.getClassLoader();
+ final ClassLoader classLoader = LoaderUtil.getClassLoader();
if (classLoader != null) {
resolver.setClassLoader(classLoader);
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginType.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginType.java
similarity index 92%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginType.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginType.java
index cc6bc66..c213f64 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/PluginType.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/PluginType.java
@@ -14,16 +14,16 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
-import org.apache.logging.log4j.core.config.plugins.processor.PluginEntry;
+import org.apache.logging.log4j.plugins.processor.PluginEntry;
/**
* Plugin Descriptor. This is a memento object for Plugin annotations paired to their annotated classes.
*
* @param <T> The plug-in class, which can be any kind of class.
- * @see org.apache.logging.log4j.core.config.plugins.Plugin
+ * @see org.apache.logging.log4j.plugins.Plugin
*/
public class PluginType<T> {
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtil.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/ResolverUtil.java
similarity index 97%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtil.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/ResolverUtil.java
index 73b5fc0..a57356c 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtil.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/ResolverUtil.java
@@ -14,33 +14,24 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.UnsupportedEncodingException;
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.util.LoaderUtil;
+import org.apache.logging.log4j.status.StatusLogger;
+import org.osgi.framework.FrameworkUtil;
+import org.osgi.framework.wiring.BundleWiring;
+
+import java.io.*;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.net.URLDecoder;
import java.nio.charset.StandardCharsets;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Enumeration;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
import java.util.jar.JarEntry;
import java.util.jar.JarInputStream;
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.util.Loader;
-import org.apache.logging.log4j.status.StatusLogger;
-import org.osgi.framework.FrameworkUtil;
-import org.osgi.framework.wiring.BundleWiring;
-
/**
* <p>
* ResolverUtil is used to locate classes that are available in the/a class path and meet arbitrary conditions. The two
@@ -126,7 +117,7 @@ public class ResolverUtil {
* @return the ClassLoader that will be used to scan for classes
*/
public ClassLoader getClassLoader() {
- return classloader != null ? classloader : (classloader = Loader.getClassLoader(ResolverUtil.class, null));
+ return classloader != null ? classloader : (classloader = LoaderUtil.getClassLoader(ResolverUtil.class, null));
}
/**
diff --git a/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/TypeUtil.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/TypeUtil.java
new file mode 100644
index 0000000..e2bb462
--- /dev/null
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/TypeUtil.java
@@ -0,0 +1,217 @@
+/*
+ * 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.plugins.util;
+
+import java.lang.reflect.*;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Objects;
+
+/**
+ * Utility class for working with Java {@link Type}s and derivatives. This class is adapted heavily from the
+ * <a href="http://projects.spring.io/spring-framework/">Spring Framework</a>, specifically the
+ * <a href="http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/util/TypeUtils.html">TypeUtils</a>
+ * class.
+ *
+ * @see Type
+ * @see GenericArrayType
+ * @see ParameterizedType
+ * @see WildcardType
+ * @see Class
+ * @since 2.1
+ */
+public final class TypeUtil {
+
+ private TypeUtil() {
+ }
+
+ /**
+ * Gets all declared fields for the given class (including superclasses).
+ *
+ * @param cls the class to examine
+ * @return all declared fields for the given class (including superclasses).
+ * @see Class#getDeclaredFields()
+ */
+ public static List<Field> getAllDeclaredFields(Class<?> cls) {
+ final List<Field> fields = new ArrayList<>();
+ while (cls != null) {
+ for (final Field field : cls.getDeclaredFields()) {
+ fields.add(field);
+ }
+ cls = cls.getSuperclass();
+ }
+ return fields;
+ }
+ /**
+ * Indicates if two {@link Type}s are assignment compatible.
+ *
+ * @param lhs the left hand side to check assignability to
+ * @param rhs the right hand side to check assignability from
+ * @return {@code true} if it is legal to assign a variable of type {@code rhs} to a variable of type {@code lhs}
+ * @see Class#isAssignableFrom(Class)
+ */
+ public static boolean isAssignable(final Type lhs, final Type rhs) {
+ Objects.requireNonNull(lhs, "No left hand side type provided");
+ Objects.requireNonNull(rhs, "No right hand side type provided");
+ if (lhs.equals(rhs)) {
+ return true;
+ }
+ if (Object.class.equals(lhs)) {
+ // everything is assignable to Object
+ return true;
+ }
+ // raw type on left
+ if (lhs instanceof Class<?>) {
+ final Class<?> lhsClass = (Class<?>) lhs;
+ if (rhs instanceof Class<?>) {
+ // no generics involved
+ final Class<?> rhsClass = (Class<?>) rhs;
+ return lhsClass.isAssignableFrom(rhsClass);
+ }
+ if (rhs instanceof ParameterizedType) {
+ // check to see if the parameterized type has the same raw type as the lhs; this is legal
+ final Type rhsRawType = ((ParameterizedType) rhs).getRawType();
+ if (rhsRawType instanceof Class<?>) {
+ return lhsClass.isAssignableFrom((Class<?>) rhsRawType);
+ }
+ }
+ if (lhsClass.isArray() && rhs instanceof GenericArrayType) {
+ // check for compatible array component types
+ return isAssignable(lhsClass.getComponentType(), ((GenericArrayType) rhs).getGenericComponentType());
+ }
+ }
+ // parameterized type on left
+ if (lhs instanceof ParameterizedType) {
+ final ParameterizedType lhsType = (ParameterizedType) lhs;
+ if (rhs instanceof Class<?>) {
+ final Type lhsRawType = lhsType.getRawType();
+ if (lhsRawType instanceof Class<?>) {
+ return ((Class<?>) lhsRawType).isAssignableFrom((Class<?>) rhs);
+ }
+ } else if (rhs instanceof ParameterizedType) {
+ final ParameterizedType rhsType = (ParameterizedType) rhs;
+ return isParameterizedAssignable(lhsType, rhsType);
+ }
+ }
+ // generic array type on left
+ if (lhs instanceof GenericArrayType) {
+ final Type lhsComponentType = ((GenericArrayType) lhs).getGenericComponentType();
+ if (rhs instanceof Class<?>) {
+ // raw type on right
+ final Class<?> rhsClass = (Class<?>) rhs;
+ if (rhsClass.isArray()) {
+ return isAssignable(lhsComponentType, rhsClass.getComponentType());
+ }
+ } else if (rhs instanceof GenericArrayType) {
+ return isAssignable(lhsComponentType, ((GenericArrayType) rhs).getGenericComponentType());
+ }
+ }
+ // wildcard type on left
+ if (lhs instanceof WildcardType) {
+ return isWildcardAssignable((WildcardType) lhs, rhs);
+ }
+ // strange...
+ return false;
+ }
+
+ private static boolean isParameterizedAssignable(final ParameterizedType lhs, final ParameterizedType rhs) {
+ if (lhs.equals(rhs)) {
+ // that was easy
+ return true;
+ }
+ final Type[] lhsTypeArguments = lhs.getActualTypeArguments();
+ final Type[] rhsTypeArguments = rhs.getActualTypeArguments();
+ final int size = lhsTypeArguments.length;
+ if (rhsTypeArguments.length != size) {
+ // clearly incompatible types
+ return false;
+ }
+ for (int i = 0; i < size; i++) {
+ // verify all type arguments are assignable
+ final Type lhsArgument = lhsTypeArguments[i];
+ final Type rhsArgument = rhsTypeArguments[i];
+ if (!lhsArgument.equals(rhsArgument) &&
+ !(lhsArgument instanceof WildcardType &&
+ isWildcardAssignable((WildcardType) lhsArgument, rhsArgument))) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ private static boolean isWildcardAssignable(final WildcardType lhs, final Type rhs) {
+ final Type[] lhsUpperBounds = getEffectiveUpperBounds(lhs);
+ final Type[] lhsLowerBounds = getEffectiveLowerBounds(lhs);
+ if (rhs instanceof WildcardType) {
+ // oh boy, this scenario requires checking a lot of assignability!
+ final WildcardType rhsType = (WildcardType) rhs;
+ final Type[] rhsUpperBounds = getEffectiveUpperBounds(rhsType);
+ final Type[] rhsLowerBounds = getEffectiveLowerBounds(rhsType);
+ for (final Type lhsUpperBound : lhsUpperBounds) {
+ for (final Type rhsUpperBound : rhsUpperBounds) {
+ if (!isBoundAssignable(lhsUpperBound, rhsUpperBound)) {
+ return false;
+ }
+ }
+ for (final Type rhsLowerBound : rhsLowerBounds) {
+ if (!isBoundAssignable(lhsUpperBound, rhsLowerBound)) {
+ return false;
+ }
+ }
+ }
+ for (final Type lhsLowerBound : lhsLowerBounds) {
+ for (final Type rhsUpperBound : rhsUpperBounds) {
+ if (!isBoundAssignable(rhsUpperBound, lhsLowerBound)) {
+ return false;
+ }
+ }
+ for (final Type rhsLowerBound : rhsLowerBounds) {
+ if (!isBoundAssignable(rhsLowerBound, lhsLowerBound)) {
+ return false;
+ }
+ }
+ }
+ } else {
+ // phew, far less bounds to check
+ for (final Type lhsUpperBound : lhsUpperBounds) {
+ if (!isBoundAssignable(lhsUpperBound, rhs)) {
+ return false;
+ }
+ }
+ for (final Type lhsLowerBound : lhsLowerBounds) {
+ if (!isBoundAssignable(lhsLowerBound, rhs)) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+
+ private static Type[] getEffectiveUpperBounds(final WildcardType type) {
+ final Type[] upperBounds = type.getUpperBounds();
+ return upperBounds.length == 0 ? new Type[]{Object.class} : upperBounds;
+ }
+
+ private static Type[] getEffectiveLowerBounds(final WildcardType type) {
+ final Type[] lowerBounds = type.getLowerBounds();
+ return lowerBounds.length == 0 ? new Type[]{null} : lowerBounds;
+ }
+
+ private static boolean isBoundAssignable(final Type lhs, final Type rhs) {
+ return (rhs == null) || ((lhs != null) && isAssignable(lhs, rhs));
+ }
+}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/package-info.java
similarity index 94%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/package-info.java
index 4f6ddda..fae7580 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/processor/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/util/package-info.java
@@ -19,4 +19,4 @@
* Java annotation processor for pre-scanning Log4j 2 plugins. This is provided as an alternative to using the
* executable {@link org.apache.logging.log4j.core.config.plugins.util.PluginManager} class in your build process.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.util;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/Constraint.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/Constraint.java
similarity index 81%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/Constraint.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/Constraint.java
index 0ac2223..4586315 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/Constraint.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/Constraint.java
@@ -14,14 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import java.lang.annotation.Annotation;
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
+import java.lang.annotation.*;
/**
* Meta annotation to mark an annotation as a validation constraint. This annotation must specify a
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidator.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidator.java
similarity index 96%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidator.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidator.java
index 1d8c0c5..2f638a7 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidator.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidator.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
import java.lang.annotation.Annotation;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidators.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidators.java
similarity index 93%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidators.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidators.java
index 374c8ec..6236bb6 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/ConstraintValidators.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/ConstraintValidators.java
@@ -14,7 +14,9 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
+
+import org.apache.logging.log4j.util.ReflectionUtil;
import java.lang.annotation.Annotation;
import java.lang.reflect.ParameterizedType;
@@ -22,8 +24,6 @@ import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.Collection;
-import org.apache.logging.log4j.core.util.ReflectionUtil;
-
/**
* Utility class to locate an appropriate {@link ConstraintValidator} implementation for an annotation.
*
@@ -36,7 +36,7 @@ public final class ConstraintValidators {
/**
* Finds all relevant {@link ConstraintValidator} objects from an array of annotations. All validators will be
- * {@link ConstraintValidator#initialize(java.lang.annotation.Annotation) initialized} before being returned.
+ * {@link ConstraintValidator#initialize(Annotation) initialized} before being returned.
*
* @param annotations the annotations to find constraint validators for
* @return a collection of ConstraintValidators for the given annotations
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/Required.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/Required.java
similarity index 73%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/Required.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/Required.java
index e6f3c56..9b8a75d 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/Required.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/Required.java
@@ -15,16 +15,12 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.validation.constraints;
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
+import org.apache.logging.log4j.plugins.validation.Constraint;
+import org.apache.logging.log4j.plugins.validation.validators.RequiredValidator;
-import org.apache.logging.log4j.core.config.plugins.validation.Constraint;
-import org.apache.logging.log4j.core.config.plugins.validation.validators.RequiredValidator;
+import java.lang.annotation.*;
/**
* Marks a plugin builder field or plugin factory parameter as required.
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidHost.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidHost.java
similarity index 84%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidHost.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidHost.java
index c652d40..14dd9a8 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidHost.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidHost.java
@@ -14,10 +14,10 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.validation.constraints;
-import org.apache.logging.log4j.core.config.plugins.validation.Constraint;
-import org.apache.logging.log4j.core.config.plugins.validation.validators.ValidHostValidator;
+import org.apache.logging.log4j.plugins.validation.Constraint;
+import org.apache.logging.log4j.plugins.validation.validators.ValidHostValidator;
import java.lang.annotation.*;
import java.net.InetAddress;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidPort.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidPort.java
similarity index 74%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidPort.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidPort.java
index a7c68b1..c4aba16 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/ValidPort.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/ValidPort.java
@@ -14,16 +14,12 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.validation.constraints;
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
+import org.apache.logging.log4j.plugins.validation.Constraint;
+import org.apache.logging.log4j.plugins.validation.validators.ValidPortValidator;
-import org.apache.logging.log4j.core.config.plugins.validation.Constraint;
-import org.apache.logging.log4j.core.config.plugins.validation.validators.ValidPortValidator;
+import java.lang.annotation.*;
/**
* Indicates that a plugin attribute must be a valid port number. A valid port number is an integer between 0 and
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/package-info.java
similarity index 91%
copy from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
copy to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/package-info.java
index f22ba49..298cd5a 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/constraints/package-info.java
@@ -20,4 +20,4 @@
*
* @since 2.1
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.validation.constraints;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/package-info.java
similarity index 93%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/package-info.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/package-info.java
index 171b25a..15955cb 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/package-info.java
@@ -20,4 +20,4 @@
*
* @since 2.1
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/RequiredValidator.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/RequiredValidator.java
similarity index 86%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/RequiredValidator.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/RequiredValidator.java
index 98c0a71..9df6d3b 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/RequiredValidator.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/RequiredValidator.java
@@ -14,17 +14,17 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.validators;
-
-import java.util.Collection;
-import java.util.Map;
+package org.apache.logging.log4j.plugins.validation.validators;
import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.validation.ConstraintValidator;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
-import org.apache.logging.log4j.core.util.Assert;
+import org.apache.logging.log4j.plugins.validation.ConstraintValidator;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.util.Assert;
import org.apache.logging.log4j.status.StatusLogger;
+import java.util.Collection;
+import java.util.Map;
+
/**
* Validator that checks an object for emptiness. Emptiness is defined here as:
* <ul>
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidHostValidator.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidHostValidator.java
similarity index 89%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidHostValidator.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidHostValidator.java
index 6c01753..41abbfd 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidHostValidator.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidHostValidator.java
@@ -14,11 +14,11 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.validators;
+package org.apache.logging.log4j.plugins.validation.validators;
import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.validation.ConstraintValidator;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.ValidHost;
+import org.apache.logging.log4j.plugins.validation.ConstraintValidator;
+import org.apache.logging.log4j.plugins.validation.constraints.ValidHost;
import org.apache.logging.log4j.status.StatusLogger;
import java.net.InetAddress;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidPortValidator.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidPortValidator.java
similarity index 85%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidPortValidator.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidPortValidator.java
index a59742c..27e97f0 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/ValidPortValidator.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/ValidPortValidator.java
@@ -14,12 +14,12 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.validators;
+package org.apache.logging.log4j.plugins.validation.validators;
import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.convert.TypeConverters;
-import org.apache.logging.log4j.core.config.plugins.validation.ConstraintValidator;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.ValidPort;
+import org.apache.logging.log4j.plugins.validation.ConstraintValidator;
+import org.apache.logging.log4j.plugins.validation.constraints.ValidPort;
+import org.apache.logging.log4j.plugins.convert.TypeConverters;
import org.apache.logging.log4j.status.StatusLogger;
/**
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/package-info.java
similarity index 92%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/package-info.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/package-info.java
index a8ac560..cfe2041 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/validators/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/validation/validators/package-info.java
@@ -20,4 +20,4 @@
*
* @since 2.1
*/
-package org.apache.logging.log4j.core.config.plugins.validation.validators;
+package org.apache.logging.log4j.plugins.validation.validators;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/AbstractPluginVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/AbstractPluginVisitor.java
similarity index 84%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/AbstractPluginVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/AbstractPluginVisitor.java
index 560cbe3..b98dc09 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/AbstractPluginVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/AbstractPluginVisitor.java
@@ -15,18 +15,18 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
+
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.plugins.convert.TypeConverters;
+import org.apache.logging.log4j.status.StatusLogger;
+import org.apache.logging.log4j.util.Strings;
import java.lang.annotation.Annotation;
import java.lang.reflect.Member;
import java.util.Map;
import java.util.Objects;
-
-import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.convert.TypeConverters;
-import org.apache.logging.log4j.core.lookup.StrSubstitutor;
-import org.apache.logging.log4j.status.StatusLogger;
-import org.apache.logging.log4j.util.Strings;
+import java.util.function.Function;
/**
* Base class for PluginVisitor implementations. Provides convenience methods as well as all method implementations
@@ -34,7 +34,7 @@ import org.apache.logging.log4j.util.Strings;
*
* @param <A> the Plugin annotation type.
*/
-public abstract class AbstractPluginVisitor<A extends Annotation> implements PluginVisitor<A> {
+public abstract class AbstractPluginVisitor<A extends Annotation, T> implements PluginVisitor<A, T> {
/** Status logger. */
protected static final Logger LOGGER = StatusLogger.getLogger();
@@ -58,10 +58,6 @@ public abstract class AbstractPluginVisitor<A extends Annotation> implements Plu
/**
*
*/
- protected StrSubstitutor substitutor;
- /**
- *
- */
protected Member member;
/**
@@ -75,7 +71,7 @@ public abstract class AbstractPluginVisitor<A extends Annotation> implements Plu
@SuppressWarnings("unchecked")
@Override
- public PluginVisitor<A> setAnnotation(final Annotation anAnnotation) {
+ public PluginVisitor<A, T> setAnnotation(final Annotation anAnnotation) {
final Annotation a = Objects.requireNonNull(anAnnotation, "No annotation was provided");
if (this.clazz.isInstance(a)) {
this.annotation = (A) a;
@@ -84,25 +80,19 @@ public abstract class AbstractPluginVisitor<A extends Annotation> implements Plu
}
@Override
- public PluginVisitor<A> setAliases(final String... someAliases) {
+ public PluginVisitor<A, T> setAliases(final String... someAliases) {
this.aliases = someAliases;
return this;
}
@Override
- public PluginVisitor<A> setConversionType(final Class<?> aConversionType) {
+ public PluginVisitor<A, T> setConversionType(final Class<?> aConversionType) {
this.conversionType = Objects.requireNonNull(aConversionType, "No conversion type class was provided");
return this;
}
@Override
- public PluginVisitor<A> setStrSubstitutor(final StrSubstitutor aSubstitutor) {
- this.substitutor = Objects.requireNonNull(aSubstitutor, "No StrSubstitutor was provided");
- return this;
- }
-
- @Override
- public PluginVisitor<A> setMember(final Member aMember) {
+ public PluginVisitor<A, T> setMember(final Member aMember) {
this.member = aMember;
return this;
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginAttributeVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginAttributeVisitor.java
similarity index 80%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginAttributeVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginAttributeVisitor.java
index f4da42b..fbd28b9 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginAttributeVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginAttributeVisitor.java
@@ -15,40 +15,39 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
-import java.util.Map;
-
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.config.plugins.PluginAttribute;
-import org.apache.logging.log4j.core.util.NameUtil;
+import org.apache.logging.log4j.plugins.Node;
+import org.apache.logging.log4j.plugins.PluginAttribute;
+import org.apache.logging.log4j.util.NameUtil;
import org.apache.logging.log4j.util.StringBuilders;
+import java.util.Map;
+import java.util.function.Function;
+
/**
* PluginVisitor implementation for {@link PluginAttribute}.
*/
-public class PluginAttributeVisitor extends AbstractPluginVisitor<PluginAttribute> {
+public class PluginAttributeVisitor extends AbstractPluginVisitor<PluginAttribute, Object> {
public PluginAttributeVisitor() {
super(PluginAttribute.class);
}
@Override
- public Object visit(final Configuration configuration, final Node node, final LogEvent event,
+ public Object visit(final Object unused, final Node node, final Function<String, String> substitutor,
final StringBuilder log) {
final String name = this.annotation.value();
final Map<String, String> attributes = node.getAttributes();
final String rawValue = removeAttributeValue(attributes, name, this.aliases);
- final String replacedValue = this.substitutor.replace(event, rawValue);
- final Object defaultValue = findDefaultValue(event);
+ final String replacedValue = substitutor.apply(rawValue);
+ final Object defaultValue = findDefaultValue(substitutor);
final Object value = convert(replacedValue, defaultValue);
final Object debugValue = this.annotation.sensitive() ? NameUtil.md5(value + this.getClass().getName()) : value;
StringBuilders.appendKeyDqValue(log, name, debugValue);
return value;
}
- private Object findDefaultValue(final LogEvent event) {
+ private Object findDefaultValue(Function<String, String> substitutor) {
if (this.conversionType == int.class || this.conversionType == Integer.class) {
return this.annotation.defaultInt();
}
@@ -76,6 +75,6 @@ public class PluginAttributeVisitor extends AbstractPluginVisitor<PluginAttribut
if (this.conversionType == Class.class) {
return this.annotation.defaultClass();
}
- return this.substitutor.replace(event, this.annotation.defaultString());
+ return substitutor.apply(this.annotation.defaultString());
}
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginBuilderAttributeVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginBuilderAttributeVisitor.java
similarity index 74%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginBuilderAttributeVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginBuilderAttributeVisitor.java
index e951456..398ff1c 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginBuilderAttributeVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginBuilderAttributeVisitor.java
@@ -15,38 +15,37 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
-import java.util.Map;
-
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.util.NameUtil;
+import org.apache.logging.log4j.plugins.Node;
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.util.NameUtil;
import org.apache.logging.log4j.util.StringBuilders;
+import java.util.Map;
+import java.util.function.Function;
+
/**
* PluginVisitor for PluginBuilderAttribute. If {@code null} is returned for the
- * {@link #visit(org.apache.logging.log4j.core.config.Configuration, org.apache.logging.log4j.core.config.Node, org.apache.logging.log4j.core.LogEvent, StringBuilder)}
+ * {@link #visit(org.apache.logging.log4j.core.config.Configuration, org.apache.logging.log4j.plugins.Node, org.apache.logging.log4j.core.LogEvent, StringBuilder)}
* method, then the default value of the field should remain untouched.
*
* @see org.apache.logging.log4j.core.config.plugins.util.PluginBuilder
*/
-public class PluginBuilderAttributeVisitor extends AbstractPluginVisitor<PluginBuilderAttribute> {
+public class PluginBuilderAttributeVisitor extends AbstractPluginVisitor<PluginBuilderAttribute, Object> {
public PluginBuilderAttributeVisitor() {
super(PluginBuilderAttribute.class);
}
@Override
- public Object visit(final Configuration configuration, final Node node, final LogEvent event,
+ public Object visit(final Object unused, final Node node, final Function<String, String> substitutor,
final StringBuilder log) {
final String overridden = this.annotation.value();
final String name = overridden.isEmpty() ? this.member.getName() : overridden;
final Map<String, String> attributes = node.getAttributes();
final String rawValue = removeAttributeValue(attributes, name, this.aliases);
- final String replacedValue = this.substitutor.replace(event, rawValue);
+ final String replacedValue = substitutor.apply(rawValue);
final Object value = convert(replacedValue, null);
final Object debugValue = this.annotation.sensitive() ? NameUtil.md5(value + this.getClass().getName()) : value;
StringBuilders.appendKeyDqValue(log, name, debugValue);
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginElementVisitor.java
similarity index 90%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginElementVisitor.java
index 2e6e6ef..f8197f1 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginElementVisitor.java
@@ -15,30 +15,29 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
+
+import org.apache.logging.log4j.plugins.Node;
+import org.apache.logging.log4j.plugins.PluginElement;
+import org.apache.logging.log4j.plugins.util.PluginType;
import java.lang.reflect.Array;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
-
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.config.plugins.PluginElement;
-import org.apache.logging.log4j.core.config.plugins.util.PluginType;
+import java.util.function.Function;
/**
* PluginVisitor implementation for {@link PluginElement}. Supports arrays as well as singular values.
*/
-public class PluginElementVisitor extends AbstractPluginVisitor<PluginElement> {
+public class PluginElementVisitor extends AbstractPluginVisitor<PluginElement, Object> {
public PluginElementVisitor() {
super(PluginElement.class);
}
@Override
- public Object visit(final Configuration configuration, final Node node, final LogEvent event,
+ public Object visit(final Object unused, final Node node, final Function<String, String> substitutor,
final StringBuilder log) {
final String name = this.annotation.value();
if (this.conversionType.isArray()) {
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginNodeVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginNodeVisitor.java
similarity index 77%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginNodeVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginNodeVisitor.java
index 7f15392..9438b39 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginNodeVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginNodeVisitor.java
@@ -15,23 +15,23 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.config.plugins.PluginNode;
+import org.apache.logging.log4j.plugins.Node;
+import org.apache.logging.log4j.plugins.PluginNode;
+
+import java.util.function.Function;
/**
* PluginVisitor implementation for {@link PluginNode}.
*/
-public class PluginNodeVisitor extends AbstractPluginVisitor<PluginNode> {
+public class PluginNodeVisitor extends AbstractPluginVisitor<PluginNode, Object> {
public PluginNodeVisitor() {
super(PluginNode.class);
}
@Override
- public Object visit(final Configuration configuration, final Node node, final LogEvent event,
+ public Object visit(final Object unused, final Node node, final Function<String, String> substitutor,
final StringBuilder log) {
if (this.conversionType.isInstance(node)) {
log.append("Node=").append(node.getName());
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginValueVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginValueVisitor.java
similarity index 79%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginValueVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginValueVisitor.java
index 8544570..2f68f04 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginValueVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginValueVisitor.java
@@ -15,26 +15,26 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.config.plugins.PluginValue;
+import org.apache.logging.log4j.plugins.Node;
+import org.apache.logging.log4j.plugins.PluginValue;
import org.apache.logging.log4j.util.StringBuilders;
import org.apache.logging.log4j.util.Strings;
+import java.util.function.Function;
+
/**
* PluginVisitor implementation for {@link PluginValue}.
*/
-public class PluginValueVisitor extends AbstractPluginVisitor<PluginValue> {
+public class PluginValueVisitor extends AbstractPluginVisitor<PluginValue, Object> {
public PluginValueVisitor() {
super(PluginValue.class);
}
@Override
- public Object visit(final Configuration configuration, final Node node, final LogEvent event,
- final StringBuilder log) {
+ public Object visit(final Object unused, final Node node, final Function<String, String> substitutor,
+ final StringBuilder log) {
final String name = this.annotation.value();
final String elementValue = node.getValue();
final String attributeValue = node.getAttributes().get("value");
@@ -49,7 +49,7 @@ public class PluginValueVisitor extends AbstractPluginVisitor<PluginValue> {
} else {
rawValue = removeAttributeValue(node.getAttributes(), "value");
}
- final String value = this.substitutor.replace(event, rawValue);
+ final String value = substitutor.apply(rawValue);
StringBuilders.appendKeyDqValue(log, name, value);
return value;
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitor.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitor.java
similarity index 68%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitor.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitor.java
index 34e2b78..fb7aca4 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitor.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitor.java
@@ -15,15 +15,13 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
+package org.apache.logging.log4j.plugins.visitors;
+
+import org.apache.logging.log4j.plugins.Node;
import java.lang.annotation.Annotation;
import java.lang.reflect.Member;
-
-import org.apache.logging.log4j.core.LogEvent;
-import org.apache.logging.log4j.core.config.Configuration;
-import org.apache.logging.log4j.core.config.Node;
-import org.apache.logging.log4j.core.lookup.StrSubstitutor;
+import java.util.function.Function;
/**
* Visitor strategy for parsing data from a {@link Node}, doing any relevant type conversion, and returning a
@@ -31,7 +29,7 @@ import org.apache.logging.log4j.core.lookup.StrSubstitutor;
*
* @param <A> the Annotation type.
*/
-public interface PluginVisitor<A extends Annotation> {
+public interface PluginVisitor<A extends Annotation, T> {
/**
* Sets the Annotation to be used for this. If the given Annotation is not compatible with this class's type, then
@@ -41,7 +39,7 @@ public interface PluginVisitor<A extends Annotation> {
* @return {@code this}.
* @throws NullPointerException if the argument is {@code null}.
*/
- PluginVisitor<A> setAnnotation(Annotation annotation);
+ PluginVisitor<A, T> setAnnotation(Annotation annotation);
/**
* Sets the list of aliases to use for this visit. No aliases are required, however.
@@ -49,7 +47,7 @@ public interface PluginVisitor<A extends Annotation> {
* @param aliases the list of aliases to use.
* @return {@code this}.
*/
- PluginVisitor<A> setAliases(String... aliases);
+ PluginVisitor<A, T> setAliases(String... aliases);
/**
* Sets the class to convert the plugin value to on this visit. This should correspond with a class obtained from
@@ -59,17 +57,7 @@ public interface PluginVisitor<A extends Annotation> {
* @return {@code this}.
* @throws NullPointerException if the argument is {@code null}.
*/
- PluginVisitor<A> setConversionType(Class<?> conversionType);
-
- /**
- * Sets the StrSubstitutor to use for converting raw strings before type conversion. Generally obtained from a
- * {@link org.apache.logging.log4j.core.config.Configuration}.
- *
- * @param substitutor the StrSubstitutor to use on plugin values.
- * @return {@code this}.
- * @throws NullPointerException if the argument is {@code null}.
- */
- PluginVisitor<A> setStrSubstitutor(StrSubstitutor substitutor);
+ PluginVisitor<A, T> setConversionType(Class<?> conversionType);
/**
* Sets the Member that this visitor is being used for injection upon. For instance, this could be the Field
@@ -79,16 +67,16 @@ public interface PluginVisitor<A extends Annotation> {
* @param member the member this visitor is parsing a value for.
* @return {@code this}.
*/
- PluginVisitor<A> setMember(Member member);
+ PluginVisitor<A, T> setMember(Member member);
/**
* Visits a Node to obtain a value for constructing a Plugin object.
*
* @param configuration the current Configuration.
* @param node the current Node corresponding to the Plugin object being created.
- * @param event the current LogEvent that caused this Plugin object to be made (optional).
- * @param log the StringBuilder being used to build a debug message.
+ * @param substitutor the function to perform String substitutions.
+ * @param log th e StringBuilder being used to build a debug message.
* @return the converted value to be used for Plugin creation.
*/
- Object visit(Configuration configuration, Node node, LogEvent event, StringBuilder log);
+ Object visit(T configuration, Node node, Function<String, String> substitutor, StringBuilder log);
}
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitors.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitors.java
similarity index 86%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitors.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitors.java
index 10ee0df..695d387 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginVisitors.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/PluginVisitors.java
@@ -15,14 +15,14 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.visitors;
-
-import java.lang.annotation.Annotation;
+package org.apache.logging.log4j.plugins.visitors;
import org.apache.logging.log4j.Logger;
-import org.apache.logging.log4j.core.config.plugins.PluginVisitorStrategy;
+import org.apache.logging.log4j.plugins.PluginVisitorStrategy;
import org.apache.logging.log4j.status.StatusLogger;
+import java.lang.annotation.Annotation;
+
/**
* Utility class to locate an appropriate {@link PluginVisitor} implementation for an annotation.
*/
@@ -41,13 +41,13 @@ public final class PluginVisitors {
* @param annotation the Plugin annotation class to find a PluginVisitor for.
* @return a PluginVisitor instance if one could be created, or {@code null} otherwise.
*/
- public static PluginVisitor<? extends Annotation> findVisitor(final Class<? extends Annotation> annotation) {
+ public static <T> PluginVisitor<? extends Annotation, T> findVisitor(final Class<? extends Annotation> annotation) {
final PluginVisitorStrategy strategy = annotation.getAnnotation(PluginVisitorStrategy.class);
if (strategy == null) {
return null;
}
try {
- return strategy.value().newInstance();
+ return (PluginVisitor<? extends Annotation, T>) strategy.value().newInstance();
} catch (final Exception e) {
LOGGER.error("Error loading PluginVisitor [{}] for annotation [{}].", strategy.value(), annotation, e);
return null;
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/package-info.java
similarity index 67%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
rename to log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/package-info.java
index f22ba49..0855b16 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/validation/constraints/package-info.java
+++ b/log4j-plugins/src/main/java/org/apache/logging/log4j/plugins/visitors/package-info.java
@@ -16,8 +16,9 @@
*/
/**
- * Validation annotations.
- *
- * @since 2.1
+ * Visitor classes for extracting values from a Configuration or Node corresponding to a plugin annotation.
+ * Visitor implementations must implement {@link org.apache.logging.log4j.plugins.visitors.PluginVisitor},
+ * and the corresponding annotation must be annotated with
+ * {@link org.apache.logging.log4j.plugins.PluginVisitorStrategy}.
*/
-package org.apache.logging.log4j.core.config.plugins.validation.constraints;
+package org.apache.logging.log4j.plugins.visitors;
diff --git a/log4j-core/src/main/resources/META-INF/services/javax.annotation.processing.Processor b/log4j-plugins/src/main/resources/META-INF/services/javax.annotation.processing.Processor
similarity index 91%
rename from log4j-core/src/main/resources/META-INF/services/javax.annotation.processing.Processor
rename to log4j-plugins/src/main/resources/META-INF/services/javax.annotation.processing.Processor
index bb9dcb9..5d6951a 100644
--- a/log4j-core/src/main/resources/META-INF/services/javax.annotation.processing.Processor
+++ b/log4j-plugins/src/main/resources/META-INF/services/javax.annotation.processing.Processor
@@ -14,4 +14,4 @@
# See the license for the specific language governing permissions and
# limitations under the license.
#
-org.apache.logging.log4j.core.config.plugins.processor.PluginProcessor
+org.apache.logging.log4j.plugins.processor.PluginProcessor
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistryTest.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistryTest.java
similarity index 97%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistryTest.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistryTest.java
index f9e757d..6e4b059 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/convert/TypeConverterRegistryTest.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/convert/TypeConverterRegistryTest.java
@@ -14,7 +14,7 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
+package org.apache.logging.log4j.plugins.convert;
import org.junit.Test;
@@ -63,7 +63,7 @@ public class TypeConverterRegistryTest {
// TODO: is there a specific converter this should return?
}
- public static enum Foo {
+ public enum Foo {
I, PITY, THE
}
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/FakePlugin.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/FakePlugin.java
similarity index 84%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/FakePlugin.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/FakePlugin.java
index f4ceb41..48ea7dc 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/FakePlugin.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/FakePlugin.java
@@ -15,10 +15,10 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginAliases;
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.plugins.PluginAliases;
/**
* Test plugin class for unit tests.
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessorTest.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/PluginProcessorTest.java
similarity index 75%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessorTest.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/PluginProcessorTest.java
index 9c37af4..034705c 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/processor/PluginProcessorTest.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/processor/PluginProcessorTest.java
@@ -15,17 +15,19 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.processor;
+package org.apache.logging.log4j.plugins.processor;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginAliases;
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.plugins.PluginAliases;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
import java.net.URL;
+import java.util.ArrayList;
import java.util.Enumeration;
+import java.util.List;
import java.util.Map;
import static org.junit.Assert.*;
@@ -33,29 +35,29 @@ import static org.junit.Assert.*;
@RunWith(JUnit4.class)
public class PluginProcessorTest {
- private static final PluginCache pluginCache = new PluginCache();
+ private static PluginService pluginService;
private final Plugin p = FakePlugin.class.getAnnotation(Plugin.class);
@BeforeClass
public static void setUpClass() throws Exception {
- final Enumeration<URL> resources =
- PluginProcessor.class.getClassLoader().getResources(PluginProcessor.PLUGIN_CACHE_FILE);
- pluginCache.loadCacheFiles(resources);
+ Class<?> clazz = PluginProcessor.class.getClassLoader().loadClass("org.apache.logging.log4j.plugins.plugins.Log4jPlugins");
+ assertNotNull("Could not locate plugins class", clazz);
+ pluginService = (PluginService) clazz.getDeclaredConstructor().newInstance();;
}
@Test
public void testTestCategoryFound() throws Exception {
assertNotNull("No plugin annotation on FakePlugin.", p);
- final Map<String, PluginEntry> testCategory = pluginCache.getCategory(p.category());
- assertNotEquals("No plugins were found.", 0, pluginCache.size());
+ final Map<String, PluginEntry> testCategory = pluginService.getCategory(p.category());
+ assertNotEquals("No plugins were found.", 0, pluginService.size());
assertNotNull("The category '" + p.category() + "' was not found.", testCategory);
assertFalse(testCategory.isEmpty());
}
@Test
public void testFakePluginFoundWithCorrectInformation() throws Exception {
- final PluginEntry fake = pluginCache.getCategory(p.category()).get(p.name().toLowerCase());
+ final PluginEntry fake = pluginService.getCategory(p.category()).get(p.name().toLowerCase());
verifyFakePluginEntry(p.name(), fake);
}
@@ -63,7 +65,7 @@ public class PluginProcessorTest {
public void testFakePluginAliasesContainSameInformation() throws Exception {
final PluginAliases aliases = FakePlugin.class.getAnnotation(PluginAliases.class);
for (final String alias : aliases.value()) {
- final PluginEntry fake = pluginCache.getCategory(p.category()).get(alias.toLowerCase());
+ final PluginEntry fake = pluginService.getCategory(p.category()).get(alias.toLowerCase());
verifyFakePluginEntry(alias, fake);
}
}
@@ -81,7 +83,7 @@ public class PluginProcessorTest {
@Test
public void testNestedPlugin() throws Exception {
final Plugin p = FakePlugin.Nested.class.getAnnotation(Plugin.class);
- final PluginEntry nested = pluginCache.getCategory(p.category()).get(p.name().toLowerCase());
+ final PluginEntry nested = pluginService.getCategory(p.category()).get(p.name().toLowerCase());
assertNotNull(nested);
assertEquals(p.name().toLowerCase(), nested.getKey());
assertEquals(FakePlugin.Nested.class.getName(), nested.getClassName());
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilCustomProtocolTest.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilCustomProtocolTest.java
similarity index 93%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilCustomProtocolTest.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilCustomProtocolTest.java
index 33e0ee1..d0b35d1 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilCustomProtocolTest.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilCustomProtocolTest.java
@@ -15,27 +15,21 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
-import static org.junit.Assert.assertEquals;
+import org.apache.logging.log4j.junit.CleanFolders;
+import org.apache.logging.log4j.junit.URLStreamHandlerFactoryRule;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.RuleChain;
import java.io.IOException;
-import java.net.Proxy;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.net.URLConnection;
-import java.net.URLStreamHandler;
-import java.net.URLStreamHandlerFactory;
+import java.net.*;
import java.util.Arrays;
import java.util.Collections;
import java.util.Enumeration;
-import org.apache.logging.log4j.core.config.plugins.util.PluginRegistry.PluginTest;
-import org.apache.logging.log4j.junit.CleanFolders;
-import org.apache.logging.log4j.junit.URLStreamHandlerFactoryRule;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.RuleChain;
+import static org.junit.Assert.assertEquals;
/**
* Tests the ResolverUtil class for custom protocol like bundleresource, vfs, vfszip.
@@ -187,9 +181,9 @@ public class ResolverUtilCustomProtocolTest {
final ResolverUtil resolverUtil = new ResolverUtil();
resolverUtil
.setClassLoader(new SingleURLClassLoader(new URL("vfs:/" + ResolverUtilTest.WORK_DIR + "/resolverutil3/customplugin3/"), cl));
- resolverUtil.findInPackage(new PluginTest(), "customplugin3");
+ resolverUtil.findInPackage(new PluginRegistry.PluginTest(), "customplugin3");
assertEquals("Class not found in packages", 1, resolverUtil.getClasses().size());
- assertEquals("Unexpected class resolved", cl.loadClass("customplugin3.FixedString3Layout"),
+ assertEquals("Unexpected class resolved", cl.loadClass("customplugin3.FixedString3"),
resolverUtil.getClasses().iterator().next());
}
}
@@ -200,9 +194,9 @@ public class ResolverUtilCustomProtocolTest {
final ResolverUtil resolverUtil = new ResolverUtil();
resolverUtil.setClassLoader(new SingleURLClassLoader(
new URL("vfs:/" + ResolverUtilTest.WORK_DIR + "/resolverutil4/customplugin4.jar/customplugin4/"), cl));
- resolverUtil.findInPackage(new PluginTest(), "customplugin4");
+ resolverUtil.findInPackage(new PluginRegistry.PluginTest(), "customplugin4");
assertEquals("Class not found in packages", 1, resolverUtil.getClasses().size());
- assertEquals("Unexpected class resolved", cl.loadClass("customplugin4.FixedString4Layout"),
+ assertEquals("Unexpected class resolved", cl.loadClass("customplugin4.FixedString4"),
resolverUtil.getClasses().iterator().next());
}
}
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilTest.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilTest.java
similarity index 82%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilTest.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilTest.java
index 1c6371b..361fe7b 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/util/ResolverUtilTest.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/util/ResolverUtilTest.java
@@ -15,33 +15,25 @@
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.util;
+package org.apache.logging.log4j.plugins.util;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-import java.net.MalformedURLException;
-import java.net.URI;
-import java.net.URISyntaxException;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.nio.file.FileSystem;
-import java.nio.file.FileSystems;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.nio.file.StandardCopyOption;
-import java.util.HashMap;
-import java.util.Map;
-
-import org.apache.logging.log4j.core.config.plugins.util.PluginRegistry.PluginTest;
import org.apache.logging.log4j.junit.CleanFolders;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.RuleChain;
+import javax.tools.*;
+import java.io.File;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.net.*;
+import java.nio.file.*;
+import java.util.*;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.assertNotNull;
+
/**
* Tests the ResolverUtil class.
*/
@@ -67,6 +59,7 @@ public class ResolverUtilTest {
private void testExtractPathFromJarUrlNotDecodedIfFileExists(final String existingFile)
throws MalformedURLException, UnsupportedEncodingException, URISyntaxException {
URL url = ResolverUtilTest.class.getResource(existingFile);
+ assertNotNull("No url returned for " + existingFile, url);
if (!url.getProtocol().equals("jar")) {
// create fake jar: URL that resolves to existing file
url = new URL("jar:" + url.toExternalForm() + "!/some/entry");
@@ -152,9 +145,9 @@ public class ResolverUtilTest {
try (final URLClassLoader cl = compileAndCreateClassLoader("1")) {
final ResolverUtil resolverUtil = new ResolverUtil();
resolverUtil.setClassLoader(cl);
- resolverUtil.findInPackage(new PluginTest(), "customplugin1");
+ resolverUtil.findInPackage(new PluginRegistry.PluginTest(), "customplugin1");
assertEquals("Class not found in packages", 1, resolverUtil.getClasses().size());
- assertEquals("Unexpected class resolved", cl.loadClass("customplugin1.FixedString1Layout"),
+ assertEquals("Unexpected class resolved", cl.loadClass("customplugin1.FixedString1"),
resolverUtil.getClasses().iterator().next());
}
}
@@ -164,9 +157,9 @@ public class ResolverUtilTest {
try (final URLClassLoader cl = compileJarAndCreateClassLoader("2")) {
final ResolverUtil resolverUtil = new ResolverUtil();
resolverUtil.setClassLoader(cl);
- resolverUtil.findInPackage(new PluginTest(), "customplugin2");
+ resolverUtil.findInPackage(new PluginRegistry.PluginTest(), "customplugin2");
assertEquals("Class not found in packages", 1, resolverUtil.getClasses().size());
- assertEquals("Unexpected class resolved", cl.loadClass("customplugin2.FixedString2Layout"),
+ assertEquals("Unexpected class resolved", cl.loadClass("customplugin2.FixedString2"),
resolverUtil.getClasses().iterator().next());
}
}
@@ -176,7 +169,7 @@ public class ResolverUtilTest {
final File jarFile = new File(workDir, "customplugin" + suffix + ".jar");
final URI jarURI = jarFile.toURI();
createJar(jarURI, workDir, new File(workDir,
- "customplugin" + suffix + "/FixedString" + suffix + "Layout.class"));
+ "customplugin" + suffix + "/FixedString" + suffix + ".class"));
return URLClassLoader.newInstance(new URL[] {jarURI.toURL()});
}
@@ -186,9 +179,9 @@ public class ResolverUtilTest {
}
static File compile(final String suffix) throws IOException {
- final File orig = new File("target/test-classes/customplugin/FixedStringLayout.java.source");
+ final File orig = new File("target/test-classes/customplugin/FixedString.java.source");
final File workDir = new File(WORK_DIR, "resolverutil" + suffix);
- final File f = new File(workDir, "customplugin" + suffix + "/FixedString" + suffix + "Layout.java");
+ final File f = new File(workDir, "customplugin" + suffix + "/FixedString" + suffix + ".java");
final File parent = f.getParentFile();
if (!parent.exists()) {
assertTrue("Create customplugin" + suffix + " folder KO", f.getParentFile().mkdirs());
@@ -199,7 +192,7 @@ public class ResolverUtilTest {
.replaceAll("customplugin", "customplugin" + suffix);
Files.write(f.toPath(), content.getBytes());
- PluginManagerPackagesTest.compile(f);
+ compile(f);
return workDir;
}
@@ -218,4 +211,29 @@ public class ResolverUtilTest {
}
}
+ static void compile(final File f) throws IOException {
+ // set up compiler
+ final JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
+ final DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<>();
+ final List<String> errors = new ArrayList<>();
+ try (final StandardJavaFileManager fileManager = compiler.getStandardFileManager(diagnostics, null, null)) {
+ final Iterable<? extends JavaFileObject> compilationUnits = fileManager.getJavaFileObjectsFromFiles(Arrays
+ .asList(f));
+
+ // compile generated source
+ // (switch off annotation processing: no need to create Log4j2Plugins.dat)
+ final List<String> options = Arrays.asList("-proc:none");
+ compiler.getTask(null, fileManager, diagnostics, options, null, compilationUnits).call();
+
+ // check we don't have any compilation errors
+ for (final Diagnostic<? extends JavaFileObject> diagnostic : diagnostics.getDiagnostics()) {
+ if (diagnostic.getKind() == Diagnostic.Kind.ERROR) {
+ errors.add(String.format("Compile error at line %d, column %d: %s%n", diagnostic.getLineNumber(),
+ diagnostic.getColumnNumber(), diagnostic.getMessage(Locale.getDefault())));
+ }
+ }
+ }
+ assertTrue(errors.toString(), errors.isEmpty());
+ }
+
}
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/AbstractPluginWithGenericBuilder.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/AbstractPluginWithGenericBuilder.java
similarity index 87%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/AbstractPluginWithGenericBuilder.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/AbstractPluginWithGenericBuilder.java
index 5689e29..0e243f2 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/AbstractPluginWithGenericBuilder.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/AbstractPluginWithGenericBuilder.java
@@ -14,10 +14,10 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
/**
*
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/HostAndPort.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/HostAndPort.java
similarity index 78%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/HostAndPort.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/HostAndPort.java
index 34123c0..626798e 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/HostAndPort.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/HostAndPort.java
@@ -14,15 +14,15 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import java.net.InetSocketAddress;
+import org.apache.logging.log4j.plugins.PluginAttribute;
+import org.apache.logging.log4j.plugins.PluginFactory;
+import org.apache.logging.log4j.plugins.validation.constraints.ValidHost;
+import org.apache.logging.log4j.plugins.validation.constraints.ValidPort;
+import org.apache.logging.log4j.plugins.Plugin;
-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.config.plugins.validation.constraints.ValidHost;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.ValidPort;
+import java.net.InetSocketAddress;
@Plugin(name = "HostAndPort", category = "Test")
public class HostAndPort {
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/PluginWithGenericSubclassFoo1Builder.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/PluginWithGenericSubclassFoo1Builder.java
similarity index 81%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/PluginWithGenericSubclassFoo1Builder.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/PluginWithGenericSubclassFoo1Builder.java
index 3f2b15a..c3fe6c5 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/PluginWithGenericSubclassFoo1Builder.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/PluginWithGenericSubclassFoo1Builder.java
@@ -14,18 +14,18 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderFactory;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.plugins.PluginBuilderFactory;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.plugins.Plugin;
@Plugin(name = "PluginWithGenericSubclassFoo1Builder", category = "Test")
public class PluginWithGenericSubclassFoo1Builder extends AbstractPluginWithGenericBuilder {
public static class Builder<B extends Builder<B>> extends AbstractPluginWithGenericBuilder.Builder<B>
- implements org.apache.logging.log4j.core.util.Builder<PluginWithGenericSubclassFoo1Builder> {
+ implements org.apache.logging.log4j.plugins.util.Builder<PluginWithGenericSubclassFoo1Builder> {
@PluginBuilderFactory
public static <B extends Builder<B>> B newBuilder() {
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPlugin.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPlugin.java
similarity index 80%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPlugin.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPlugin.java
index 95a4209..9caf453 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPlugin.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPlugin.java
@@ -14,15 +14,15 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import java.util.Objects;
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.plugins.PluginBuilderFactory;
+import org.apache.logging.log4j.plugins.PluginFactory;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderFactory;
-import org.apache.logging.log4j.core.config.plugins.PluginFactory;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
+import java.util.Objects;
/**
*
@@ -51,7 +51,7 @@ public class ValidatingPlugin {
return new Builder();
}
- public static class Builder implements org.apache.logging.log4j.core.util.Builder<ValidatingPlugin> {
+ public static class Builder implements org.apache.logging.log4j.plugins.util.Builder<ValidatingPlugin> {
@PluginBuilderAttribute
@Required(message = "The name given by the builder is null")
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithGenericBuilder.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithGenericBuilder.java
similarity index 80%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithGenericBuilder.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithGenericBuilder.java
index 81b9d6f..b0bec53 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithGenericBuilder.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithGenericBuilder.java
@@ -14,15 +14,16 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import java.util.Objects;
+import org.apache.logging.log4j.plugins.Plugin;
+
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.plugins.PluginBuilderFactory;
+import org.apache.logging.log4j.plugins.PluginFactory;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderFactory;
-import org.apache.logging.log4j.core.config.plugins.PluginFactory;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
+import java.util.Objects;
/**
*
@@ -51,7 +52,7 @@ public class ValidatingPluginWithGenericBuilder {
return new Builder<B>().asBuilder();
}
- public static class Builder<B extends Builder<B>> implements org.apache.logging.log4j.core.util.Builder<ValidatingPluginWithGenericBuilder> {
+ public static class Builder<B extends Builder<B>> implements org.apache.logging.log4j.plugins.util.Builder<ValidatingPluginWithGenericBuilder> {
@PluginBuilderAttribute
@Required(message = "The name given by the builder is null")
diff --git a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithTypedBuilder.java b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithTypedBuilder.java
similarity index 80%
rename from log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithTypedBuilder.java
rename to log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithTypedBuilder.java
index 74a6477..256181c 100644
--- a/log4j-core/src/test/java/org/apache/logging/log4j/core/config/plugins/validation/ValidatingPluginWithTypedBuilder.java
+++ b/log4j-plugins/src/test/java/org/apache/logging/log4j/plugins/validation/ValidatingPluginWithTypedBuilder.java
@@ -14,15 +14,15 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.validation;
+package org.apache.logging.log4j.plugins.validation;
-import java.util.Objects;
+import org.apache.logging.log4j.plugins.PluginBuilderAttribute;
+import org.apache.logging.log4j.plugins.PluginBuilderFactory;
+import org.apache.logging.log4j.plugins.PluginFactory;
+import org.apache.logging.log4j.plugins.validation.constraints.Required;
+import org.apache.logging.log4j.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.Plugin;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderAttribute;
-import org.apache.logging.log4j.core.config.plugins.PluginBuilderFactory;
-import org.apache.logging.log4j.core.config.plugins.PluginFactory;
-import org.apache.logging.log4j.core.config.plugins.validation.constraints.Required;
+import java.util.Objects;
/**
*
@@ -51,7 +51,7 @@ public class ValidatingPluginWithTypedBuilder {
return new Builder<>();
}
- public static class Builder<T> implements org.apache.logging.log4j.core.util.Builder<ValidatingPluginWithTypedBuilder> {
+ public static class Builder<T> implements org.apache.logging.log4j.plugins.util.Builder<ValidatingPluginWithTypedBuilder> {
@PluginBuilderAttribute
@Required(message = "The name given by the builder is null")
diff --git a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java b/log4j-plugins/src/test/resources/customplugin/FixedString.java.source
similarity index 52%
rename from log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java
rename to log4j-plugins/src/test/resources/customplugin/FixedString.java.source
index 15a162c..85a62ec 100644
--- a/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/convert/EnumConverter.java
+++ b/log4j-plugins/src/test/resources/customplugin/FixedString.java.source
@@ -14,25 +14,32 @@
* See the license for the specific language governing permissions and
* limitations under the license.
*/
-package org.apache.logging.log4j.core.config.plugins.convert;
-import org.apache.logging.log4j.util.EnglishEnums;
+package customplugin;
-/**
- * Converts a {@link String} into a {@link Enum}. Returns {@code null} for invalid enum names.
- *
- * @param <E> the enum class to parse.
- * @since 2.1 moved from TypeConverters
- */
-public class EnumConverter<E extends Enum<E>> implements TypeConverter<E> {
- private final Class<E> clazz;
+import java.util.Collections;
+import java.util.Map;
+
+import org.apache.logging.log4j.plugins.Plugin;
+import org.apache.logging.log4j.plugins.PluginAttribute;
+import org.apache.logging.log4j.plugins.PluginFactory;
+
+@Plugin(name = "FixedString", category = "Core", elementType = "plugin", printObject = true)
+public class FixedString {
+
+ private String fixedString;
+
+ @PluginFactory
+ public static FixedString create(
+ @PluginAttribute("fixedString") final String fixedString) {
+ return new FixedString(fixedString);
+ }
- public EnumConverter(final Class<E> clazz) {
- this.clazz = clazz;
+ public FixedString(String fixedString) {
+ this.fixedString = fixedString;
}
- @Override
- public E convert(final String s) {
- return EnglishEnums.valueOf(clazz, s);
+ public Map<String, String> getContentFormat() {
+ return Collections.emptyMap();
}
}
diff --git a/log4j-plugins/src/test/resources/log4j+config+with+plus+characters.xml b/log4j-plugins/src/test/resources/log4j+config+with+plus+characters.xml
new file mode 100644
index 0000000..b85475a
--- /dev/null
+++ b/log4j-plugins/src/test/resources/log4j+config+with+plus+characters.xml
@@ -0,0 +1,31 @@
+<?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 status="OFF" name="XMLConfigTest">
+
+ <Appenders>
+ <List name="List">
+ </List>
+ </Appenders>
+ <Loggers>
+ <Root level="trace">
+ <AppenderRef ref="List"/>
+ </Root>
+ </Loggers>
+
+</Configuration>
\ No newline at end of file
diff --git a/log4j-plugins/src/test/resources/s p a c e s/log4j+config+with+plus+characters.xml b/log4j-plugins/src/test/resources/s p a c e s/log4j+config+with+plus+characters.xml
new file mode 100644
index 0000000..b85475a
--- /dev/null
+++ b/log4j-plugins/src/test/resources/s p a c e s/log4j+config+with+plus+characters.xml
@@ -0,0 +1,31 @@
+<?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 status="OFF" name="XMLConfigTest">
+
+ <Appenders>
+ <List name="List">
+ </List>
+ </Appenders>
+ <Loggers>
+ <Root level="trace">
+ <AppenderRef ref="List"/>
+ </Root>
+ </Loggers>
+
+</Configuration>
\ No newline at end of file