Author: mattsicker
Date: Mon May 26 06:02:28 2014
New Revision: 1597517
URL: http://svn.apache.org/r1597517
Log:
Add PluginElement visitor implementation.
- This is by far the hardest one to both get right and clean up.
I've only been able to clean up a little from the original code
this is based on, so please feel free to offer improvements if you
can figure this out!
- Moved the list of used nodes to directly modify the
Node.getChildren() list (outside iteration of course!) instead of
relying on a field.
- I noticed a bit of inconsistency in how a child node's object is
checked for null: when there's an array of elements, null objects
are warned about in the log. When there's a single element, a null
object is happily returned without any logging. Does this make sense?
Added:
logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
(with props)
Added:
logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java?rev=1597517&view=auto
==============================================================================
---
logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
(added)
+++
logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
Mon May 26 06:02:28 2014
@@ -0,0 +1,102 @@
+/*
+ * 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.visitors;
+
+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;
+
+/**
+ * PluginVisitor implementation for {@link PluginElement}. Supports arrays as
well as singular values.
+ */
+public class PluginElementVisitor extends AbstractPluginVisitor<PluginElement>
{
+ public PluginElementVisitor() {
+ super(PluginElement.class);
+ }
+
+ @Override
+ public Object visit(final Configuration configuration, final Node node,
final LogEvent event) {
+ final String name = this.annotation.value();
+ if (this.conversionType.isArray()) {
+ setConversionType(this.conversionType.getComponentType());
+ final List<Object> values = new ArrayList<Object>();
+ final Collection<Node> used = new ArrayList<Node>();
+ for (final Node child : node.getChildren()) {
+ final PluginType<?> childType = child.getType();
+ if (name.equalsIgnoreCase(childType.getElementName()) ||
+
this.conversionType.isAssignableFrom(childType.getPluginClass())) {
+ used.add(child);
+ final Object childObject = child.getObject();
+ if (childObject == null) {
+ LOGGER.error("Null object returned for {} in {}.",
child.getName(), node.getName());
+ continue;
+ }
+ if (childObject.getClass().isArray()) {
+ final Object[] o = (Object[]) childObject;
+ LOGGER.debug("{}={}", name, Arrays.toString(o));
+ return childObject;
+ }
+ values.add(childObject);
+ }
+ }
+ // note that we need to return an empty array instead of null if
the types are correct
+ if (!values.isEmpty() &&
!this.conversionType.isAssignableFrom(values.get(0).getClass())) {
+ LOGGER.error("Attempted to assign attribute {} to list of type
{} which is incompatible with {}.",
+ name, values.get(0).getClass(), this.conversionType);
+ return null;
+ }
+ node.getChildren().removeAll(used);
+ LOGGER.debug("{}={}", name, values);
+ // we need to use reflection here because values.toArray() will
cause type errors at runtime
+ final Object[] array = (Object[])
Array.newInstance(this.conversionType, values.size());
+ for (int i = 0; i < array.length; i++) {
+ array[i] = values.get(i);
+ }
+ return array;
+ } else {
+ final Node namedNode = findNamedNode(name, node.getChildren());
+ if (namedNode == null) {
+ return null;
+ }
+ LOGGER.debug("{}({})", namedNode.getName(), namedNode.toString());
+ node.getChildren().remove(namedNode);
+ return namedNode.getObject();
+ }
+ }
+
+ private Node findNamedNode(final String name, final Iterable<Node>
children) {
+ for (final Node child : children) {
+ final PluginType<?> childType = child.getType();
+ if (name.equalsIgnoreCase(childType.getElementName()) ||
+
this.conversionType.isAssignableFrom(childType.getPluginClass())) {
+ // FIXME: check child.getObject() for null?
+ // doing so would be more consistent with the array version
+ return child;
+ }
+ }
+ return null;
+ }
+}
Propchange:
logging/log4j/log4j2/trunk/log4j-core/src/main/java/org/apache/logging/log4j/core/config/plugins/visitors/PluginElementVisitor.java
------------------------------------------------------------------------------
svn:eol-style = native