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.logging.log4j.core.filter;
018
019import java.util.Iterator;
020
021import org.apache.logging.log4j.Logger;
022import org.apache.logging.log4j.core.Filter;
023import org.apache.logging.log4j.core.LifeCycle;
024import org.apache.logging.log4j.core.LogEvent;
025import org.apache.logging.log4j.status.StatusLogger;
026
027/**
028 * Enhances a Class by allowing it to contain Filters.
029 */
030public abstract class AbstractFilterable implements Filterable {
031
032    protected static final Logger LOGGER = StatusLogger.getLogger();
033
034    private volatile Filter filter;
035
036    protected AbstractFilterable(final Filter filter) {
037        this.filter = filter;
038    }
039
040    protected AbstractFilterable() {
041    }
042
043    /**
044     * Returns the Filter.
045     * @return the Filter.
046     */
047    @Override
048    public Filter getFilter() {
049        return filter;
050    }
051
052    /**
053     * Add a filter.
054     * @param filter The Filter to add.
055     */
056    @Override
057    public synchronized void addFilter(final Filter filter) {
058        if (this.filter == null) {
059            this.filter = filter;
060        } else if (filter instanceof CompositeFilter) {
061            this.filter = ((CompositeFilter) this.filter).addFilter(filter);
062        } else {
063            final Filter[] filters = new Filter[] {this.filter, filter};
064            this.filter = CompositeFilter.createFilters(filters);
065        }
066    }
067
068    /**
069     * Remove a Filter.
070     * @param filter The Filter to remove.
071     */
072    @Override
073    public synchronized void removeFilter(final Filter filter) {
074        if (this.filter == filter) {
075            this.filter = null;
076        } else if (filter instanceof CompositeFilter) {
077            CompositeFilter composite = (CompositeFilter) filter;
078            composite = composite.removeFilter(filter);
079            if (composite.size() > 1) {
080                this.filter = composite;
081            } else if (composite.size() == 1) {
082                final Iterator<Filter> iter = composite.iterator();
083                this.filter = iter.next();
084            } else {
085                this.filter = null;
086            }
087        }
088    }
089
090    /**
091     * Determines if a Filter is present.
092     * @return false if no Filter is present.
093     */
094    @Override
095    public boolean hasFilter() {
096        return filter != null;
097    }
098
099    /**
100     * Make the Filter available for use.
101     */
102    public void startFilter() {
103       if (filter instanceof LifeCycle) {
104           ((LifeCycle) filter).start();
105       }
106    }
107
108    /**
109     * Cleanup the Filter.
110     */
111    public void stopFilter() {
112       if (filter instanceof LifeCycle) {
113           ((LifeCycle) filter).stop();
114       }
115    }
116
117    /**
118     * Determine if the LogEvent should be processed or ignored.
119     * @param event The LogEvent.
120     * @return true if the LogEvent should be processed.
121     */
122    @Override
123    public boolean isFiltered(final LogEvent event) {
124        return filter != null && filter.filter(event) == Filter.Result.DENY;
125    }
126
127}