    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.commons.configuration;
    018
    019    import org.apache.commons.logging.Log;
    020    import org.apache.commons.logging.LogFactory;
    021    import org.apache.commons.logging.impl.NoOpLog;
    022
    023    import java.io.InputStream;
    024    import java.io.OutputStream;
    025    import java.io.File;
    026    import java.net.URL;
    027    import java.net.MalformedURLException;
    028
    029    /**
    030     * Abstract layer to allow various types of file systems.
    031     * @since 1.7
    032     * @author <a
    033     * href="http://commons.apache.org/configuration/team-list.html">Commons Configuration team</a>
    034     */
    035    public abstract class FileSystem
    036    {
    037        /** The name of the system property that can be used to set the file system class name */
    038        private static final String FILE_SYSTEM = "org.apache.commons.configuration.filesystem";
    039
    040        /** The default file system */
    041        private static FileSystem fileSystem;
    042
    043        /** The Logger */
    044        private Log log;
    045
    046        /** FileSystem options provider */
    047        private FileOptionsProvider optionsProvider;
    048
    049        public FileSystem()
    050        {
    051            setLogger(null);
    052        }
    053
    054        /**
    055         * Returns the logger used by this FileSystem.
    056         *
    057         * @return the logger
    058         */
    059        public Log getLogger()
    060        {
    061            return log;
    062        }
    063
    064        /**
    065         * Allows to set the logger to be used by this FileSystem. This
    066         * method makes it possible for clients to exactly control logging behavior.
    067         * Per default a logger is set that will ignore all log messages. Derived
    068         * classes that want to enable logging should call this method during their
    069         * initialization with the logger to be used.
    070         *
    071         * @param log the new logger
    072         */
    073        public void setLogger(Log log)
    074        {
    075            this.log = (log != null) ? log : new NoOpLog();
    076        }
    077
    078        static
    079        {
    080            String fsClassName = System.getProperty(FILE_SYSTEM);
    081            if (fsClassName != null)
    082            {
    083                Log log = LogFactory.getLog(FileSystem.class);
    084
    085                try
    086                {
    087                    Class clazz = Class.forName(fsClassName);
    088                    if (FileSystem.class.isAssignableFrom(clazz))
    089                    {
    090                        fileSystem = (FileSystem) clazz.newInstance();
    091                        if (log.isDebugEnabled())
    092                        {
    093                            log.debug("Using " + fsClassName);
    094                        }
    095                    }
    096                }
    097                catch (InstantiationException ex)
    098                {
    099                    log.error("Unable to create " + fsClassName, ex);
    100                }
    101                catch (IllegalAccessException ex)
    102                {
    103                    log.error("Unable to create " + fsClassName, ex);
    104                }
    105                catch (ClassNotFoundException ex)
    106                {
    107                    log.error("Unable to create " + fsClassName, ex);
    108                }
    109            }
    110
    111            if (fileSystem == null)
    112            {
    113                fileSystem = new DefaultFileSystem();
    114            }
    115        }
    116
    117        /**
    118         * Set the FileSystem to use.
    119         * @param fs The FileSystem
    120         * @throws NullPointerException if the FileSystem parameter is null.
    121         */
    122        public static void setDefaultFileSystem(FileSystem fs) throws NullPointerException
    123        {
    124            if (fs == null)
    125            {
    126                throw new NullPointerException("A FileSystem implementation is required");
    127            }
    128            fileSystem = fs;
    129        }
    130
    131        /**
    132         * Reset the FileSystem to the default.
    133         */
    134        public static void resetDefaultFileSystem()
    135        {
    136            fileSystem = new DefaultFileSystem();
    137        }
    138
    139        /**
    140         * Retrieve the FileSystem being used.
    141         * @return The FileSystem.
    142         */
    143        public static FileSystem getDefaultFileSystem()
    144        {
    145            return fileSystem;
    146        }
    147
    148        /**
    149         * Set the FileOptionsProvider
    150         * @param provider The FileOptionsProvider
    151         */
    152        public void setFileOptionsProvider(FileOptionsProvider provider)
    153        {
    154            this.optionsProvider = provider;
    155        }
    156
    157        public FileOptionsProvider getFileOptionsProvider()
    158        {
    159            return this.optionsProvider;
    160        }
    161
    162        public abstract InputStream getInputStream(String basePath, String fileName)
    163                throws ConfigurationException;
    164
    165        public abstract InputStream getInputStream(URL url) throws ConfigurationException;
    166
    167        public abstract OutputStream getOutputStream(URL url) throws ConfigurationException;
    168
    169        public abstract OutputStream getOutputStream(File file) throws ConfigurationException;
    170
    171        public abstract String getPath(File file, URL url, String basePath, String fileName);
    172
    173        public abstract String getBasePath(String path);
    174
    175        public abstract String getFileName(String path);
    176
    177        public abstract URL locateFromURL(String basePath, String fileName);
    178
    179        public abstract URL getURL(String basePath, String fileName) throws MalformedURLException;
    180    }