001package org.apache.fulcrum.yaafi.framework.util;
002
003/*
004 * Licensed to the Apache Software Foundation (ASF) under one
005 * or more contributor license agreements.  See the NOTICE file
006 * distributed with this work for additional information
007 * regarding copyright ownership.  The ASF licenses this file
008 * to you under the Apache License, Version 2.0 (the
009 * "License"); you may not use this file except in compliance
010 * with the License.  You may obtain a copy of the License at
011 *
012 *   http://www.apache.org/licenses/LICENSE-2.0
013 *
014 * Unless required by applicable law or agreed to in writing,
015 * software distributed under the License is distributed on an
016 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
017 * KIND, either express or implied.  See the License for the
018 * specific language governing permissions and limitations
019 * under the License.
020 */
021
022import java.io.File;
023import java.io.FileInputStream;
024import java.io.IOException;
025import java.io.InputStream;
026
027import org.apache.avalon.framework.logger.Logger;
028import org.apache.avalon.framework.logger.NullLogger;
029
030/**
031 * Helper for locating a file name and returning an input stream.
032 *
033 * @author <a href="mailto:siegfried.goeschl@it20one.at">Siegfried Goeschl</a>
034 */
035
036public class InputStreamLocator {
037        
038        /** the root directory of our search */
039        private File rootDir;
040
041        /** the logger to be used */
042        private Logger logger;
043
044        /**
045         * Constructor
046         */
047        public InputStreamLocator() {
048                this.rootDir = new File(new File("").getAbsolutePath());
049                this.logger = new NullLogger();
050        }
051
052        /**
053         * Constructor
054         *
055         * @param rootDir the root directory to start the search
056         */
057        public InputStreamLocator(File rootDir) {
058                this(rootDir, new NullLogger());
059        }
060
061        /**
062         * Constructor
063         *
064         * @param rootDir the root directory to start the search
065         * @param logger  the logger to be used
066         */
067        public InputStreamLocator(File rootDir, Logger logger) {
068                this.rootDir = rootDir;
069                this.logger = logger;
070        }
071
072        /**
073         * Locate the file with the given position using the following steps
074         *
075         * @param location the location of the source to be loaded
076         * @return input stream of the source
077         * @throws IOException if source is not found
078         */
079        public InputStream locate(String location) throws IOException {
080                if (location == null || location.length() == 0) {
081                        return null;
082                }
083
084                String baseName = null;
085                File file = null;
086                InputStream is = null;
087
088                // try to load a relative location with the given root dir
089                // e.g. "componentRoles.xml" located in the current working directory
090                if (is == null) {
091                        file = new File(this.rootDir, location);
092
093                        this.logger.debug("Looking for " + location + " in the root directory");
094
095                        if (file.exists()) {
096                                is = new FileInputStream(file);
097                                this.logger.debug("Found " + location + " as " + file.getAbsolutePath());
098                        }
099                }
100
101                // try to load an absolute location as file
102                // e.g. "/foo/componentRoles.xml" from the root of the file system
103                if (is == null) {
104                        file = new File(location);
105
106                        this.logger.debug("Looking for " + location + " as absolute file location");
107
108                        if (file.isAbsolute() && file.exists()) {
109                                is = new FileInputStream(file);
110                                this.logger.debug("Found " + location + " as " + file.getAbsolutePath());
111                        }
112                }
113
114                // try to load an absolute location through the classpath
115                // e.g. "/componentRoles.xml" located in the classpath
116                if (is == null && location.startsWith("/") == true) {
117                        this.logger.debug("Looking for " + location + " using the class loader");
118                        is = getClass().getResourceAsStream(location);
119
120                        if (is != null) {
121                                this.logger.debug("Successfully located " + location);
122                        }
123                }
124
125                // try to load the last part of the file name using the classloader
126                // e.g. "conf/componentRoles.xml" as "/componentRoles.xml" located in
127                // the classpath.
128
129                if (is == null && location.startsWith("/") == false) {
130                        baseName = '/' + new File(location).getName();
131                        this.logger.debug("Looking for " + baseName + " using the class loader");
132                        is = getClass().getResourceAsStream(baseName);
133                        if (is != null) {
134                                this.logger.debug("Successfully located " + baseName);
135                        }
136                }
137
138                if (is == null) {
139                        this.logger.debug("Unable to find any resource with the name '" + location + "'");
140                }
141
142                return is;
143        }
144
145        /**
146         * @return Returns the rootDir.
147         */
148        protected File getRootDir() {
149                return rootDir;
150        }
151
152}