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     */
017    package org.apache.camel.component.file;
018    
019    import java.io.File;
020    import java.io.FileFilter;
021    
022    import org.apache.camel.util.AntPathMatcher;
023    import org.slf4j.Logger;
024    import org.slf4j.LoggerFactory;
025    
026    /**
027     * File filter using {@link AntPathMatcher}.
028     * <p/>
029     * Exclude take precedence over includes. If a file match both exclude and include it will be regarded as excluded.
030     */
031    public class AntPathMatcherFileFilter implements FileFilter {
032        private static final Logger LOG = LoggerFactory.getLogger(AntPathMatcherFileFilter.class);
033    
034        private AntPathMatcher matcher = new AntPathMatcher();
035        private String[] excludes;
036        private String[] includes;
037        private boolean caseSensitive = true;
038    
039        public boolean accept(File pathname) {
040            return acceptPathName(pathname.getPath());
041        }
042    
043        /**
044         * Accepts the given file by the path name
045         *
046         * @param path the path
047         * @return <tt>true</tt> if accepted, <tt>false</tt> if not
048         */
049        public boolean acceptPathName(String path) {
050            // must use single / as path separators
051            path = path.replace(File.separatorChar, '/');
052    
053            LOG.trace("Filtering file: {}", path);
054    
055            // excludes take precedence
056            if (excludes != null) {
057                for (String exclude : excludes) {
058                    if (matcher.match(exclude, path, caseSensitive)) {
059                        // something to exclude so we cant accept it
060                        LOG.trace("File is excluded: {}", path);
061                        return false;
062                    }
063                }
064            }
065    
066            if (includes != null) {
067                for (String include : includes) {
068                    if (matcher.match(include, path, caseSensitive)) {
069                        // something to include so we accept it
070                        LOG.trace("File is included: {}", path);
071                        return true;
072                    }
073                }
074            }
075    
076            if (excludes != null && includes == null) {
077                // if the user specified excludes but no includes, presumably we should include by default
078                return true;
079            }
080    
081            // nothing to include so we can't accept it
082            return false;
083        }
084    
085        /**
086         *
087         * @return <tt>true</tt> if case sensitive pattern matching is on,
088         * <tt>false</tt> if case sensitive pattern matching is off.
089         */
090        public boolean isCaseSensitive() {
091            return caseSensitive;
092        }
093    
094        /**
095         * Sets Whether or not pattern matching should be case sensitive
096         * <p/>
097         * Is by default turned on <tt>true</tt>.
098         * @param caseSensitive <tt>false</tt> to disable case sensitive pattern matching
099         */
100        public void setCaseSensitive(boolean caseSensitive) {
101            this.caseSensitive = caseSensitive;
102        }
103    
104        public String[] getExcludes() {
105            return excludes;
106        }
107    
108        public void setExcludes(String[] excludes) {
109            this.excludes = excludes;
110        }
111    
112        public String[] getIncludes() {
113            return includes;
114        }
115    
116        public void setIncludes(String[] includes) {
117            this.includes = includes;
118        }
119    
120        /**
121         * Sets excludes using a single string where each element can be separated with comma
122         */
123        public void setExcludes(String excludes) {
124            setExcludes(excludes.split(","));
125        }
126    
127        /**
128         * Sets includes using a single string where each element can be separated with comma
129         */
130        public void setIncludes(String includes) {
131            setIncludes(includes.split(","));
132        }
133    
134    }