You are viewing a plain text version of this content. The canonical link for it is here.
Posted to log4j-dev@logging.apache.org by ce...@apache.org on 2005/01/03 12:01:02 UTC

cvs commit: logging-log4j/src/java/org/apache/log4j/filter LevelMatchFilter.java MapFilter.java ReflectionFilter.java ExpressionFilter.java StringMatchFilter.java LocationInfoFilter.java LevelRangeFilter.java DenyAllFilter.java PropertyFilter.java

ceki        2005/01/03 03:01:02

  Added:       src/java/org/apache/log4j/filter LevelMatchFilter.java
                        MapFilter.java ReflectionFilter.java
                        ExpressionFilter.java StringMatchFilter.java
                        LocationInfoFilter.java LevelRangeFilter.java
                        DenyAllFilter.java PropertyFilter.java
  Log:
  Singular is the preferred form for package names. filters -> filter
  
  Revision  Changes    Path
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/LevelMatchFilter.java
  
  Index: LevelMatchFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   *
   * Licensed 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.log4j.filter;
  
  import org.apache.log4j.Level;
  import org.apache.log4j.helpers.OptionConverter;
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  
  /**
     This is a very simple filter based on level matching.
  
     <p>The filter admits two options <b>LevelToMatch</b> and
     <b>AcceptOnMatch</b>. If there is an exact match between the value
     of the <b>LevelToMatch</b> option and the level of the {@link
     LoggingEvent}, then the {@link #decide} method returns {@link
     Filter#ACCEPT} in case the <b>AcceptOnMatch</b> option value is set
     to <code>true</code>, if it is <code>false</code> then {@link
     Filter#DENY} is returned. If there is no match, {@link
     Filter#NEUTRAL} is returned.
  
     @author Ceki G&uuml;lc&uuml;
  
     @since 1.2 */
  public class LevelMatchFilter extends Filter {
    /**
       Do we return ACCEPT when a match occurs. Default is
       <code>true</code>.  */
    boolean acceptOnMatch = true;
  
    /**
     */
    Level levelToMatch;
  
    public void setLevelToMatch(String level) {
      levelToMatch = OptionConverter.toLevel(level, null);
    }
  
    public String getLevelToMatch() {
      return (levelToMatch == null) ? null : levelToMatch.toString();
    }
  
    public void setAcceptOnMatch(boolean acceptOnMatch) {
      this.acceptOnMatch = acceptOnMatch;
    }
  
    public boolean getAcceptOnMatch() {
      return acceptOnMatch;
    }
  
  
    /**
       Return the decision of this filter.
  
       Returns {@link Filter#NEUTRAL} if the <b>LevelToMatch</b> option
       is not set or if there is not match.  Otherwise, if there is a
       match, then the returned decision is {@link Filter#ACCEPT} if the
       <b>AcceptOnMatch</b> property is set to <code>true</code>. The
       returned decision is {@link Filter#DENY} if the
       <b>AcceptOnMatch</b> property is set to false.
  
    */
    public int decide(LoggingEvent event) {
      if (this.levelToMatch == null) {
        return Filter.NEUTRAL;
      }
  
      boolean matchOccured = false;
  
      if (this.levelToMatch.equals(event.getLevel())) {
        matchOccured = true;
      }
  
      if (matchOccured) {
        if (this.acceptOnMatch) {
          return Filter.ACCEPT;
        } else {
          return Filter.DENY;
        }
      } else {
        return Filter.NEUTRAL;
      }
    }
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/MapFilter.java
  
  Index: MapFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   * 
   * Licensed 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.log4j.filter;
  
  import java.util.Hashtable;
  import java.util.Iterator;
  import java.util.Map;
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  public class MapFilter extends Filter {
  
  	/**
  	 * NOTE: This filter modifies logging events by adding properties to the event.
  	 * 
  	 * The object passed in as the event message must implement java.util.Map.
     * 
     * This filter converts the event message (a Map) into properties on the event.
     * 
     * If the map holds an entry with a key of "message", the value of the entry is used
     * as the rendered message.
     * 
  	 * @since 1.3
  	 */
  	public int decide(LoggingEvent event) {
  		Map properties = event.getProperties();
  		Hashtable eventProps = null;
  		if (properties == null) {
  			eventProps = new Hashtable();
  		} else {
  			eventProps = new Hashtable(properties);
  		}
  	
  		if (event.getMessage() instanceof Map) {
  			for (Iterator iter = ((Map)event.getMessage()).entrySet().iterator();iter.hasNext();) {
          Map.Entry entry = (Map.Entry)iter.next();
  				if ("message".equalsIgnoreCase(entry.getKey().toString())) {
  					event.setRenderedMessage(entry.getValue().toString());
  				} else {
  					eventProps.put(entry.getKey(), entry.getValue());
  				}
  			}
  			event.setProperties(eventProps);
  		}
  		return Filter.NEUTRAL;
  	}
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/ReflectionFilter.java
  
  Index: ReflectionFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   * 
   * Licensed 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.log4j.filter;
  
  import java.beans.IntrospectionException;
  import java.beans.Introspector;
  import java.beans.PropertyDescriptor;
  import java.lang.reflect.InvocationTargetException;
  import java.util.Hashtable;
  import java.util.Map;
  
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  public class ReflectionFilter extends Filter {
  
  	/**
  	 * NOTE: This filter modifies logging events by adding   
  	 * properties to the event.
  	 * 
  	 * The object passed in as the message must provide a message via toString 
  	 * or provide a 'message' property, which will be set as the rendered message.
  	 * 
  	 * This ReflectionFilter uses the JavaBeans BeanInfo and PropertyDescriptor mechanisms to discover 
  	 * readMethods available on the 'message' object provided by the event.
  	 *  
  	 * For each method available on the object via the BeanInfo PropertyDescriptors, the method is executed
  	 * and a property is added to the event, using the results of the method call as the value 
  	 * and the method name as the key.
  	 * 
  	 * @since 1.3
  	 */
  	public int decide(LoggingEvent event) {
  		Map properties = event.getProperties();
  		Hashtable eventProps = null;
  		if (properties == null) {
  			eventProps = new Hashtable();
  		} else {
  			eventProps = new Hashtable(properties);
  		}
  	
  		//ignore strings and the object class properties
  		if (!(event.getMessage() instanceof String)) {
  			PropertyDescriptor[] props;
  			try {
  				props = Introspector.getBeanInfo(event.getMessage().getClass(), Object.class).getPropertyDescriptors();
  				for (int i=0;i<props.length;i++) {
  					if ("message".equalsIgnoreCase(props[i].getName())) {
  						event.setRenderedMessage(props[i].getReadMethod().invoke(event.getMessage(), null).toString());
  					} else {
  						eventProps.put(props[i].getName(), props[i].getReadMethod().invoke(event.getMessage(), null).toString());
  					}
  				}
  				event.setProperties(eventProps);
  			} catch (IntrospectionException e) {
  				e.printStackTrace();
  			} catch (IllegalArgumentException e1) {
  				e1.printStackTrace();
  			} catch (IllegalAccessException e1) {
  				e1.printStackTrace();
  			} catch (InvocationTargetException e1) {
  				e1.printStackTrace();
  			}
  		}
  		return Filter.NEUTRAL;
  	}
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/ExpressionFilter.java
  
  Index: ExpressionFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   * 
   * Licensed 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.log4j.filter;
  
  import org.apache.log4j.rule.ExpressionRule;
  import org.apache.log4j.rule.Rule;
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  
  /**
   *A filter supporting complex expressions - supports both infix and postfix expressions 
   *(infix expressions must first be converted to postfix prior to processing).
   *
   *See <code>org.apache.log4j.chainsaw.LoggingEventFieldResolver.java</code> 
   *for the correct names for logging event fields used when building expressions.
   *
   *See <org.apache.log4j.chainsaw.rule</code> package for a list of available rules which can
   *be applied using the expression syntax.
   *
   *See <code>org.apache.log4j.chainsaw.RuleFactory</code> for the symbols used to 
   *activate the corresponding rules.
   *
   *NOTE:  Grouping using parentheses is supported - all tokens must be separated by spaces, and
   *operands which contain spaces are not yet supported.
   *
   *Example:
   *
   *In order to build a filter that displays all messages with infomsg-45 or infomsg-44 in the message,
   *as well as all messages with a level of WARN or higher, build an expression using 
   *the LikeRule (supports ORO-based regular expressions) and the InequalityRule. 
   * <b> ( MSG LIKE infomsg-4[4,5] ) && ( LEVEL >= WARN ) </b>
   *  
   *Three options are required:
   *  <b>Expression</b> - the expression to match
   *  <b>ConvertInFixToPostFix</b> - convert from infix to posfix (default true)
   *  <b>AcceptOnMatch</b> - true or false (default true)
   *
   * Meaning of <b>AcceptToMatch</b>:
   * If there is a match between the value of the
   * Expression option and the {@link LoggingEvent} and AcceptOnMatch is true,
   * the {@link #decide} method returns {@link Filter#ACCEPT}.
   *
   * If there is a match between the value of the
   * Expression option and the {@link LoggingEvent} and AcceptOnMatch is false,
   * {@link Filter#DENY} is returned.
   *
   * If there is no match, {@link Filter#NEUTRAL} is returned.
   *
   * @author Scott Deboy sdeboy@apache.org
   */
  public class ExpressionFilter extends Filter {
    boolean acceptOnMatch = true;
    boolean convertInFixToPostFix = true;
    String expression;
    Rule expressionRule;
  
    public void activateOptions() {
      expressionRule =
        ExpressionRule.getRule(expression, !convertInFixToPostFix);
    }
  
    public void setExpression(String expression) {
      this.expression = expression;
    }
  
    public String getExpression() {
      return expression;
    }
  
    public void setConvertInFixToPostFix(boolean convertInFixToPostFix) {
      this.convertInFixToPostFix = convertInFixToPostFix;
    }
  
    public boolean getConvertInFixToPostFix() {
      return convertInFixToPostFix;
    }
  
    public void setAcceptOnMatch(boolean acceptOnMatch) {
      this.acceptOnMatch = acceptOnMatch;
    }
  
    public boolean getAcceptOnMatch() {
      return acceptOnMatch;
    }
  
    /**
       Returns {@link Filter#NEUTRAL} is there is no string match.
     */
    public int decide(LoggingEvent event) {
      if (expressionRule.evaluate(event)) {
        return (acceptOnMatch?Filter.ACCEPT:Filter.DENY);
      }
      return Filter.NEUTRAL;
    }
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/StringMatchFilter.java
  
  Index: StringMatchFilter.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  
  package org.apache.log4j.filter;
  
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  /**
     This is a very simple filter based on string matching.
     
  
     <p>The filter admits two options <b>StringToMatch</b> and
     <b>AcceptOnMatch</b>. If there is a match between the value of the
     StringToMatch option and the message of the {@link LoggingEvent},
     then the {@link #decide} method returns {@link Filter#ACCEPT} if
     the <b>AcceptOnMatch</b> option value is true, if it is false then
     {@link Filter#DENY} is returned. If there is no match, {@link
     Filter#NEUTRAL} is returned.
  
     @author Ceki G&uuml;lc&uuml;
  
     @since 0.9.0 */
  public class StringMatchFilter extends Filter {
    
    boolean acceptOnMatch = true;
    String stringToMatch;
    
    public
    void setStringToMatch(String s) {
      stringToMatch = s;
    }
    
    public
    String getStringToMatch() {
      return stringToMatch;
    }
    
    public
    void setAcceptOnMatch(boolean acceptOnMatch) {
      this.acceptOnMatch = acceptOnMatch;
    }
    
    public
    boolean getAcceptOnMatch() {
      return acceptOnMatch;
    }
  
    /**
       Returns {@link Filter#NEUTRAL} is there is no string match.
     */
    public
    int decide(LoggingEvent event) {
      String msg = event.getRenderedMessage();
  
      if(msg == null ||  stringToMatch == null)
        return Filter.NEUTRAL;
      
  
      if( msg.indexOf(stringToMatch) == -1 ) {
        return Filter.NEUTRAL;
      } else { // we've got a match
        if(acceptOnMatch) {
  	return Filter.ACCEPT;
        } else {
  	return Filter.DENY;
        }
      }
    }
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/LocationInfoFilter.java
  
  Index: LocationInfoFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   * 
   * Licensed 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.log4j.filter;
  
  import org.apache.log4j.rule.ExpressionRule;
  import org.apache.log4j.rule.Rule;
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  import org.apache.log4j.spi.location.LocationInfo;
  
  
  /**
   * Location information is usually specified at the appender level - all events associated 
   * with an appender either create and parse stack traces or they do not.  This is
   * an expensive operation and in some cases not needed for all events associated with
   * an appender.
   * 
   * This filter creates event-level location information only if the provided expression evaluates to true.
   * 
   * For information on expression syntax, see org.apache.log4j.rule.ExpressionRule
   * 
   * @author Scott Deboy sdeboy@apache.org
   */
  public class LocationInfoFilter extends Filter {
    boolean convertInFixToPostFix = true;
    String expression;
    Rule expressionRule;
    //HACK: Category is the last of the internal layers - pass this in as the class name
    //in order for parsing to work correctly
    private String className = "org.apache.log4j.Category";
  
    public void activateOptions() {
      expressionRule =
        ExpressionRule.getRule(expression, !convertInFixToPostFix);
    }
  
    public void setExpression(String expression) {
      this.expression = expression;
    }
  
    public String getExpression() {
      return expression;
    }
  
    public void setConvertInFixToPostFix(boolean convertInFixToPostFix) {
      this.convertInFixToPostFix = convertInFixToPostFix;
    }
  
    public boolean getConvertInFixToPostFix() {
      return convertInFixToPostFix;
    }
  
    /**
     * If this event does not already contain location information, 
     * evaluate the event against the expression.
     * 
     * If the expression evaluates to true, generate a LocationInfo instance 
     * by creating an exception and set this LocationInfo on the event.
     * 
     * Returns {@link Filter#NEUTRAL}
     */
    public int decide(LoggingEvent event) {
      if (!event.locationInformationExists()) {
        if (expressionRule.evaluate(event)) {
  	      Throwable t = new Exception();
  	      event.setLocationInformation(new LocationInfo(t, className));
        }
      }
      return Filter.NEUTRAL;
    }
  }
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/LevelRangeFilter.java
  
  Index: LevelRangeFilter.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software
   * License version 1.1, a copy of which has been included with this
   * distribution in the LICENSE.txt file.  */
  
  package org.apache.log4j.filter;
  
  import org.apache.log4j.Level;
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  /**
     This is a very simple filter based on level matching, which can be
     used to reject messages with priorities outside a certain range.
     
     <p>The filter admits three options <b>LevelMin</b>, <b>LevelMax</b>
     and <b>AcceptOnMatch</b>.
  
     <p>If the level of the {@link LoggingEvent} is not between Min and Max
     (inclusive), then {@link Filter#DENY} is returned.
     
     <p> If the Logging event level is within the specified range, then if
     <b>AcceptOnMatch</b> is true, {@link Filter#ACCEPT} is returned, and if
     <b>AcceptOnMatch</b> is false, {@link Filter#NEUTRAL} is returned.
     
     <p>If <code>LevelMin</code>w is not defined, then there is no
     minimum acceptable level (ie a level is never rejected for
     being too "low"/unimportant).  If <code>LevelMax</code> is not
     defined, then there is no maximum acceptable level (ie a
     level is never rejected for beeing too "high"/important).
  
     <p>Refer to the {@link
     org.apache.log4j.AppenderSkeleton#setThreshold setThreshold} method
     available to <code>all</code> appenders extending {@link
     org.apache.log4j.AppenderSkeleton} for a more convenient way to
     filter out events by level.
  
     @author Simon Kitching
     @author based on code by Ceki G&uuml;lc&uuml; 
  */
  public class LevelRangeFilter extends Filter {
  
    /**
       Do we return ACCEPT when a match occurs. Default is
       <code>false</code>, so that later filters get run by default  */
    boolean acceptOnMatch = false;
  
    Level levelMin;
    Level levelMax;
  
   
    /**
       Return the decision of this filter.
     */
    public
    int decide(LoggingEvent event) {
      if(this.levelMin != null) {
        if (event.getLevel().isGreaterOrEqual(levelMin) == false) {
          // level of event is less than minimum
          return Filter.DENY;
        }
      }
  
      if(this.levelMax != null) {
        if (event.getLevel().toInt() > levelMax.toInt()) {
          // level of event is greater than maximum
          // Alas, there is no Level.isGreater method. and using
          // a combo of isGreaterOrEqual && !Equal seems worse than
          // checking the int values of the level objects..
          return Filter.DENY;
        }
      }
  
      if (acceptOnMatch) {
        // this filter set up to bypass later filters and always return
        // accept if level in range
        return Filter.ACCEPT;
      }
      else {
        // event is ok for this filter; allow later filters to have a look..
        return Filter.NEUTRAL;
      }
    }
  
   /**
       Get the value of the <code>LevelMax</code> option.  */
    public
    Level getLevelMax() {
      return levelMax;
    }
  
  
    /**
       Get the value of the <code>LevelMin</code> option.  */
    public
    Level getLevelMin() {
      return levelMin;
    }
  
    /**
       Get the value of the <code>AcceptOnMatch</code> option.
     */
    public
    boolean getAcceptOnMatch() {
      return acceptOnMatch;
    }
  
    /**
       Set the <code>LevelMax</code> option.
     */
    public
    void setLevelMax(Level levelMax) {
      this.levelMax =  levelMax;
    }
  
    /**
       Set the <code>LevelMin</code> option.
     */
    public
    void setLevelMin(Level levelMin) {
      this.levelMin =  levelMin;
    }
  
    /**
       Set the <code>AcceptOnMatch</code> option.
     */  
    public 
    void setAcceptOnMatch(boolean acceptOnMatch) {
      this.acceptOnMatch = acceptOnMatch;
    }
  }
  
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/DenyAllFilter.java
  
  Index: DenyAllFilter.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  
  package org.apache.log4j.filter;
  
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  
  /**
     This filter drops all logging events. 
  
     <p>You can add this filter to the end of a filter chain to
     switch from the default "accept all unless instructed otherwise"
     filtering behaviour to a "deny all unless instructed otherwise"
     behaviour.
  
  
     @author Ceki G&uuml;lc&uuml;
  
     @since 0.9.0 */
  public class DenyAllFilter extends Filter {
  
    /**
       Returns <code>null</code> as there are no options.
       
       @deprecated We now use JavaBeans introspection to configure
       components. Options strings are no longer needed.
    */
    public
    String[] getOptionStrings() {
      return null;
    }
  
    
    /**
       No options to set.
       
       @deprecated Use the setter method for the option directly instead
       of the generic <code>setOption</code> method. 
    */
    public
    void setOption(String key, String value) {
    }
    
    /**
       Always returns the integer constant {@link Filter#DENY}
       regardless of the {@link LoggingEvent} parameter.
  
       @param event The LoggingEvent to filter.
       @return Always returns {@link Filter#DENY}.
    */
    public
    int decide(LoggingEvent event) {
      return Filter.DENY;
    }
  }
  
  
  
  
  1.1                  logging-log4j/src/java/org/apache/log4j/filter/PropertyFilter.java
  
  Index: PropertyFilter.java
  ===================================================================
  /*
   * Copyright 1999,2004 The Apache Software Foundation.
   * 
   * Licensed 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.log4j.filter;
  
  import java.util.Hashtable;
  import java.util.Iterator;
  import java.util.Map;
  import java.util.StringTokenizer;
  
  import org.apache.log4j.spi.Filter;
  import org.apache.log4j.spi.LoggingEvent;
  
  /**
   * NOTE: This filter modifies logging events by adding properties to the event.
   * 
   * The 'properties' param is converted to event properties, which are 
   * set on every event processed by the filter.
   * 
   * Individual properties are only set if they do not already exist on the 
   * logging event (will not override existing properties).
   * 
   * This class relies on the convention that property name/value pairs are 
   * equals-symbol delimited, and each name/value pair is comma-delimited
   * 
   * Example properties param:
   * somename=somevalue,anothername=anothervalue,thirdname=third value
   * 
   * @since 1.3
   */
  public class PropertyFilter extends Filter {
  	private Hashtable properties;
  	public void setProperties(String props) {
  		properties = parseProperties(props);
  	}
  	
  	public int decide(LoggingEvent event) {
  		Map eventProps = event.getProperties();
  		if (eventProps == null) {
  			event.setProperties(new Hashtable(properties));
  		} else {
  		    //only add properties that don't already exist
  		    for (Iterator iter = properties.keySet().iterator();iter.hasNext();) {
  		        Object key = iter.next();
  		        if (!(eventProps.containsKey(key))) {
  		            eventProps.put(key, properties.get(key));
  		        }
  		    }
  		}
  		return Filter.NEUTRAL;
  	}
  	
  	private Hashtable parseProperties(String props) {
  		Hashtable hashTable = new Hashtable();
  		StringTokenizer pairs = new StringTokenizer(props, ",");
  		while (pairs.hasMoreTokens()) {
  			StringTokenizer entry = new StringTokenizer(pairs.nextToken(), "=");
  			hashTable.put(entry.nextElement().toString().trim(), entry.nextElement().toString().trim());
  		}
  		return hashTable;
  	}
  }
  
  
  

---------------------------------------------------------------------
To unsubscribe, e-mail: log4j-dev-unsubscribe@logging.apache.org
For additional commands, e-mail: log4j-dev-help@logging.apache.org