/*******************************************************************************
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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.ofbiz.base.location;

import java.net.MalformedURLException;
import java.net.URL;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.Map.Entry;

import org.ofbiz.base.util.Debug;
import org.ofbiz.base.util.UtilProperties;
import org.ofbiz.base.util.UtilValidate;

/**
 * A special location resolver that uses Strings like URLs, but with more options.
 *
 */

public final class FlexibleLocation {

    public static final String module = FlexibleLocation.class.getName();
    private static final Map<String, LocationResolver> locationResolvers;

    static {
        Map<String, LocationResolver> resolverMap = new HashMap<String, LocationResolver>(8);
        LocationResolver standardUrlResolver = new StandardUrlLocationResolver();
        resolverMap.put("http", standardUrlResolver);
        resolverMap.put("https", standardUrlResolver);
        resolverMap.put("ftp", standardUrlResolver);
        resolverMap.put("jar", standardUrlResolver);
        resolverMap.put("file", standardUrlResolver);
        resolverMap.put("classpath", new ClasspathLocationResolver());
        resolverMap.put("ofbizhome", new OFBizHomeLocationResolver());
        resolverMap.put("component", new ComponentLocationResolver());
        try {
            Properties properties = UtilProperties.getProperties("locationresolvers.properties");
            if (properties != null) {
                ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
                for (Entry<Object, Object> entry : properties.entrySet()) {
                    String locationType = (String) entry.getKey();
                    String locationResolverName = (String) entry.getValue();
                    Class<?> lClass = classLoader.loadClass(locationResolverName);
                    resolverMap.put(locationType, (LocationResolver) lClass.newInstance());
                }
            }
        } catch (Throwable e) {
            Debug.logWarning(e, "Error while loading resolvers from locationresolvers.properties: ", module);
        }
        locationResolvers = Collections.unmodifiableMap(resolverMap);
    }

    /**
     * Find the location type descriptor for the passed location String;
     *   generally is all text before the first ":" character.
     *   If no type descriptor is found, defaults to "classpath".
     */
    private static String getLocationType(String location) {
        int colonIndex = location.indexOf(":");
        if (colonIndex > 0) {
            return location.substring(0, colonIndex);
        } else {
            return "classpath";
        }
    }

    /**
     * Resolves the gives location into a URL object for use in various ways.
     *
     * The general format of the location is like a URL: {locationType}://location/path/file.ext
     *
     * Supports standard locationTypes like http, https, ftp, jar, & file
     * Supports a classpath location type for when desired to be used like any other URL
     * Supports OFBiz specific location types like ofbizhome and component
     * Supports additional locationTypes specified in the locationresolvers.properties file
     *
     * @param location The location String to parse and create a URL from
     * @return URL object corresponding to the location String passed in
     * @throws MalformedURLException
     */
    public static URL resolveLocation(String location) throws MalformedURLException {
        return resolveLocation(location, null);
    }

    public static URL resolveLocation(String location, ClassLoader loader) throws MalformedURLException {
        if (UtilValidate.isEmpty(location)) {
            return null;
        }
        String locationType = getLocationType(location);
        LocationResolver resolver = locationResolvers.get(locationType);
        if (resolver != null) {
            if (loader != null && resolver instanceof ClasspathLocationResolver) {
                ClasspathLocationResolver cplResolver = (ClasspathLocationResolver) resolver;
                return cplResolver.resolveLocation(location, loader);
            } else {
                return resolver.resolveLocation(location);
            }
        } else {
            throw new MalformedURLException("Could not find a LocationResolver for the location type: " + locationType);
        }
    }

    public static String stripLocationType(String location) {
        if (UtilValidate.isEmpty(location)) {
            return "";
        }
        StringBuilder strippedSoFar = new StringBuilder(location);
        // first take care of the colon and everything before it
        int colonIndex = strippedSoFar.indexOf(":");
        if (colonIndex == 0) {
            strippedSoFar.deleteCharAt(0);
        } else if (colonIndex > 0) {
            strippedSoFar.delete(0, colonIndex + 1);
        }
        // now remove any extra forward slashes, ie as long as the first two are forward slashes remove the first one
        while (strippedSoFar.charAt(0) == '/' && strippedSoFar.charAt(1) == '/') {
            strippedSoFar.deleteCharAt(0);
        }
        return strippedSoFar.toString();
    }

    private FlexibleLocation() {}
}
