001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache license, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the license for the specific language governing permissions and 015 * limitations under the license. 016 */ 017package org.apache.log4j.builders.appender; 018 019import static org.apache.log4j.builders.BuilderManager.CATEGORY; 020import static org.apache.log4j.config.Log4j1Configuration.APPENDER_REF_TAG; 021import static org.apache.log4j.config.Log4j1Configuration.THRESHOLD_PARAM; 022import static org.apache.log4j.xml.XmlConfiguration.FILTER_TAG; 023import static org.apache.log4j.xml.XmlConfiguration.NAME_ATTR; 024import static org.apache.log4j.xml.XmlConfiguration.PARAM_TAG; 025import static org.apache.log4j.xml.XmlConfiguration.VALUE_ATTR; 026import static org.apache.log4j.xml.XmlConfiguration.forEachElement; 027 028import java.util.ArrayList; 029import java.util.List; 030import java.util.Properties; 031import java.util.concurrent.atomic.AtomicReference; 032 033import org.apache.log4j.Appender; 034import org.apache.log4j.bridge.AppenderWrapper; 035import org.apache.log4j.bridge.RewritePolicyAdapter; 036import org.apache.log4j.bridge.RewritePolicyWrapper; 037import org.apache.log4j.builders.AbstractBuilder; 038import org.apache.log4j.config.Log4j1Configuration; 039import org.apache.log4j.config.PropertiesConfiguration; 040import org.apache.log4j.helpers.OptionConverter; 041import org.apache.log4j.rewrite.RewritePolicy; 042import org.apache.log4j.spi.Filter; 043import org.apache.log4j.xml.XmlConfiguration; 044import org.apache.logging.log4j.Logger; 045import org.apache.logging.log4j.core.appender.rewrite.RewriteAppender; 046import org.apache.logging.log4j.core.config.AppenderRef; 047import org.apache.logging.log4j.core.config.plugins.Plugin; 048import org.apache.logging.log4j.status.StatusLogger; 049import org.apache.logging.log4j.util.Strings; 050import org.w3c.dom.Element; 051 052 053/** 054 * Build an Asynch Appender 055 */ 056@Plugin(name = "org.apache.log4j.rewrite.RewriteAppender", category = CATEGORY) 057public class RewriteAppenderBuilder extends AbstractBuilder implements AppenderBuilder { 058 059 private static final Logger LOGGER = StatusLogger.getLogger(); 060 private static final String REWRITE_POLICY_TAG = "rewritePolicy"; 061 062 public RewriteAppenderBuilder() { 063 } 064 065 public RewriteAppenderBuilder(String prefix, Properties props) { 066 super(prefix, props); 067 } 068 069 @Override 070 public Appender parseAppender(final Element appenderElement, final XmlConfiguration config) { 071 String name = appenderElement.getAttribute(NAME_ATTR); 072 AtomicReference<List<String>> appenderRefs = new AtomicReference<>(new ArrayList<>()); 073 AtomicReference<RewritePolicy> rewritePolicyHolder = new AtomicReference<>(); 074 AtomicReference<String> level = new AtomicReference<>(); 075 AtomicReference<Filter> filter = new AtomicReference<>(); 076 forEachElement(appenderElement.getChildNodes(), currentElement -> { 077 switch (currentElement.getTagName()) { 078 case APPENDER_REF_TAG: 079 Appender appender = config.findAppenderByReference(currentElement); 080 if (appender != null) { 081 appenderRefs.get().add(appender.getName()); 082 } 083 break; 084 case REWRITE_POLICY_TAG: { 085 RewritePolicy policy = config.parseRewritePolicy(currentElement); 086 if (policy != null) { 087 rewritePolicyHolder.set(policy); 088 } 089 break; 090 } 091 case FILTER_TAG: { 092 filter.set(config.parseFilters(currentElement)); 093 break; 094 } 095 case PARAM_TAG: { 096 if (currentElement.getAttribute(NAME_ATTR).equalsIgnoreCase(THRESHOLD_PARAM)) { 097 String value = currentElement.getAttribute(VALUE_ATTR); 098 if (value == null) { 099 LOGGER.warn("No value supplied for Threshold parameter, ignoring."); 100 } else { 101 level.set(value); 102 } 103 } 104 break; 105 } 106 } 107 }); 108 return createAppender(name, level.get(), appenderRefs.get().toArray(Strings.EMPTY_ARRAY), rewritePolicyHolder.get(), 109 filter.get(), config); 110 } 111 112 @Override 113 public Appender parseAppender(final String name, final String appenderPrefix, final String layoutPrefix, 114 final String filterPrefix, final Properties props, final PropertiesConfiguration configuration) { 115 String appenderRef = getProperty(APPENDER_REF_TAG); 116 Filter filter = configuration.parseAppenderFilters(props, filterPrefix, name); 117 String policyPrefix = appenderPrefix + ".rewritePolicy"; 118 String className = getProperty(policyPrefix); 119 RewritePolicy policy = configuration.getBuilderManager().parseRewritePolicy(className, policyPrefix, 120 props, configuration); 121 String level = getProperty(THRESHOLD_PARAM); 122 if (appenderRef == null) { 123 LOGGER.warn("No appender references configured for AsyncAppender {}", name); 124 return null; 125 } 126 Appender appender = configuration.parseAppender(props, appenderRef); 127 if (appender == null) { 128 LOGGER.warn("Cannot locate Appender {}", appenderRef); 129 return null; 130 } 131 return createAppender(name, level, new String[] {appenderRef}, policy, filter, configuration); 132 } 133 134 private <T extends Log4j1Configuration> Appender createAppender(String name, String level, 135 String[] appenderRefs, RewritePolicy policy, Filter filter, T configuration) { 136 org.apache.logging.log4j.Level logLevel = OptionConverter.convertLevel(level, 137 org.apache.logging.log4j.Level.TRACE); 138 AppenderRef[] refs = new AppenderRef[appenderRefs.length]; 139 int index = 0; 140 for (String appenderRef : appenderRefs) { 141 refs[index++] = AppenderRef.createAppenderRef(appenderRef, logLevel, null); 142 } 143 org.apache.logging.log4j.core.Filter rewriteFilter = buildFilters(level, filter); 144 org.apache.logging.log4j.core.appender.rewrite.RewritePolicy rewritePolicy; 145 if (policy instanceof RewritePolicyWrapper) { 146 rewritePolicy = ((RewritePolicyWrapper) policy).getPolicy(); 147 } else { 148 rewritePolicy = new RewritePolicyAdapter(policy); 149 } 150 return new AppenderWrapper(RewriteAppender.createAppender(name, "true", refs, configuration, 151 rewritePolicy, rewriteFilter)); 152 } 153}