/*
 * 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.
 */

/* $Id$ */

package org.apache.fop.apps.io;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.URI;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;

import org.apache.xmlgraphics.io.Resource;
import org.apache.xmlgraphics.io.ResourceResolver;
import org.apache.xmlgraphics.io.TempResourceResolver;
import org.apache.xmlgraphics.io.TempResourceURIGenerator;

/**
 * A factory class for {@link ResourceResolver}s.
 */
public final class ResourceResolverFactory {

    private ResourceResolverFactory() {
    }

    /**
     * Returns the default resource resolver, this is most basic resolver which can be used when
     * no there are no I/O or file access restrictions.
     *
     * @return the default resource resolver
     */
    public static ResourceResolver createDefaultResourceResolver() {
        return DefaultResourceResolver.INSTANCE;
    }

    /**
     * A helper merthod that creates an internal resource resolver using the default resover:
     * {@link ResourceResolverFactory#createDefaultResourceResolver()}.
     *
     * @param baseURI the base URI from which to resolve URIs
     * @return the default internal resource resolver
     */
    public static InternalResourceResolver createDefaultInternalResourceResolver(URI baseURI) {
        return new InternalResourceResolver(baseURI, createDefaultResourceResolver());
    }

    /**
     * Creates an interal resource resolver given a base URI and a resource resolver.
     *
     * @param baseURI the base URI from which to resolve URIs
     * @param resolver the resource resolver
     * @return the internal resource resolver
     */
    public static InternalResourceResolver createInternalResourceResolver(URI baseURI,
            ResourceResolver resolver) {
        return new InternalResourceResolver(baseURI, resolver);
    }

    /**
     * Creates a temporary-resource-scheme aware resource resolver. Temporary resource URIs are
     * created by {@link TempResourceURIGenerator}.
     *
     * @param tempResourceResolver the temporary-resource-scheme resolver to use
     * @param defaultResourceResolver the default resource resolver to use
     * @return the ressource resolver
     */
    public static ResourceResolver createTempAwareResourceResolver(
            TempResourceResolver tempResourceResolver,
            ResourceResolver defaultResourceResolver) {
        return new TempAwareResourceResolver(tempResourceResolver, defaultResourceResolver);
    }

    /**
     * This creates the builder class for binding URI schemes to implementations of
     * {@link ResourceResolver}. This allows users to define their own URI schemes such that they
     * have finer control over the acquisition of resources.
     *
     * @param defaultResolver the default resource resolver that should be used in the event that
     * none of the other registered resolvers match the scheme
     * @return the scheme aware {@link ResourceResolver} builder
     */
    public static SchemeAwareResourceResolverBuilder createSchemeAwareResourceResolverBuilder(
            ResourceResolver defaultResolver) {
        return new SchemeAwareResourceResolverBuilderImpl(defaultResolver);
    }

    private static final class DefaultResourceResolver implements ResourceResolver {

        private static final ResourceResolver INSTANCE = new DefaultResourceResolver();

        private final TempAwareResourceResolver delegate;

        private DefaultResourceResolver() {
            delegate = new TempAwareResourceResolver(new DefaultTempResourceResolver(),
                    new NormalResourceResolver());
        }

        /** {@inheritDoc} */
        public Resource getResource(URI uri) throws IOException {
            return delegate.getResource(uri);
        }

        /** {@inheritDoc} */
        public OutputStream getOutputStream(URI uri) throws IOException {
            return delegate.getOutputStream(uri);
        }

    }

    private static final class TempAwareResourceResolver implements ResourceResolver {

        private final TempResourceResolver tempResourceResolver;

        private final ResourceResolver defaultResourceResolver;

        public TempAwareResourceResolver(TempResourceResolver tempResourceHandler,
                ResourceResolver defaultResourceResolver) {
            this.tempResourceResolver = tempResourceHandler;
            this.defaultResourceResolver = defaultResourceResolver;
        }

        private static boolean isTempURI(URI uri) {
            return TempResourceURIGenerator.isTempURI(uri);
        }

        /** {@inheritDoc} */
        public Resource getResource(URI uri) throws IOException {
            if (isTempURI(uri)) {
                return tempResourceResolver.getResource(uri.getPath());
            } else {
                return defaultResourceResolver.getResource(uri);
            }
        }

        /** {@inheritDoc} */
        public OutputStream getOutputStream(URI uri) throws IOException {
            if (isTempURI(uri)) {
                return tempResourceResolver.getOutputStream(uri.getPath());
            } else {
                return defaultResourceResolver.getOutputStream(uri);
            }
        }
    }

    private static class DefaultTempResourceResolver implements TempResourceResolver {
        private static File getTempFile(String path) throws IOException {
            File file = new File(System.getProperty("java.io.tmpdir"), path);
            file.deleteOnExit();
            return file;
        }

        /** {@inheritDoc} */
        public Resource getResource(String id) throws IOException {
            return new Resource(getTempFile(id).toURI().toURL().openStream());
        }

        /** {@inheritDoc} */
        public OutputStream getOutputStream(String id) throws IOException {
            File file = getTempFile(id);
            if (file.createNewFile()) {
                return new FileOutputStream(file);
            } else {
                throw new IOException("Filed to create temporary file: " + id);
            }
        }
    }

    private static class NormalResourceResolver implements ResourceResolver {
        public Resource getResource(URI uri) throws IOException {
            return new Resource(uri.toURL().openStream());
        }

        public OutputStream getOutputStream(URI uri) throws IOException {
            return new FileOutputStream(new File(uri));
        }
    }

    private static final class SchemeAwareResourceResolver implements ResourceResolver {

        private final Map<String, ResourceResolver> schemeHandlingResourceResolvers;

        private final ResourceResolver defaultResolver;

        private SchemeAwareResourceResolver(
                Map<String, ResourceResolver> schemEHandlingResourceResolvers,
                ResourceResolver defaultResolver) {
            this.schemeHandlingResourceResolvers = schemEHandlingResourceResolvers;
            this.defaultResolver = defaultResolver;
        }

        private ResourceResolver getResourceResolverForScheme(URI uri) {
            String scheme = uri.getScheme();
            if (schemeHandlingResourceResolvers.containsKey(scheme)) {
                return schemeHandlingResourceResolvers.get(scheme);
            } else {
                return defaultResolver;
            }
        }

        /** {@inheritDoc} */
        public Resource getResource(URI uri) throws IOException {
            return getResourceResolverForScheme(uri).getResource(uri);
        }

        /** {@inheritDoc} */
        public OutputStream getOutputStream(URI uri) throws IOException {
            return getResourceResolverForScheme(uri).getOutputStream(uri);
        }
    }

    /**
     * Implementations of this interface will be builders for {@link ResourceResolver}, they bind
     * URI schemes to their respective resolver. This gives users more control over the mechanisms
     * by which URIs are resolved.
     * <p>
     * Here is an example of how this could be used:
     * </p>
     * <p><code>
     * SchemeAwareResourceResolverBuilder builder
     *      = ResourceResolverFactory.createSchemeAwareResourceResolverBuilder(defaultResolver);
     * builder.registerResourceResolverForScheme("test", testResolver);
     * builder.registerResourceResolverForScheme("anotherTest", test2Resolver);
     * ResourceResolver resolver = builder.build();
     * </code></p>
     * This will result in all URIs for the form "test:///..." will be resolved using the
     * <code>testResolver</code> object; URIs of the form "anotherTest:///..." will be resolved
     * using <code>test2Resolver</code>; all other URIs will be resolved from the defaultResolver.
     */
    public interface SchemeAwareResourceResolverBuilder {

        /**
         * Register a scheme with its respective {@link ResourceResolver}. This resolver will be
         * used as the only resolver for the specified scheme.
         *
         * @param scheme the scheme to be used with the given resolver
         * @param resourceResolver the resource resolver
         */
        void registerResourceResolverForScheme(String scheme, ResourceResolver resourceResolver);

        /**
         * Builds a {@link ResourceResolver} that will delegate to the respective resource resolver
         * when a registered URI scheme is given
         *
         * @return a resolver that delegates to the appropriate scheme resolver
         */
        ResourceResolver build();
    }

    private static final class CompletedSchemeAwareResourceResolverBuilder
            implements SchemeAwareResourceResolverBuilder {

        private static final SchemeAwareResourceResolverBuilder INSTANCE
                = new CompletedSchemeAwareResourceResolverBuilder();

        /** {@inheritDoc} */
        public ResourceResolver build() {
            throw new IllegalStateException("Resource resolver already built");
        }

        /** {@inheritDoc} */
        public void registerResourceResolverForScheme(String scheme,
                ResourceResolver resourceResolver) {
            throw new IllegalStateException("Resource resolver already built");
        }
    }

    private static final class ActiveSchemeAwareResourceResolverBuilder
            implements SchemeAwareResourceResolverBuilder {

        private final Map<String, ResourceResolver> schemeHandlingResourceResolvers
                = new HashMap<String, ResourceResolver>();

        private final ResourceResolver defaultResolver;

        private ActiveSchemeAwareResourceResolverBuilder(ResourceResolver defaultResolver) {
            this.defaultResolver = defaultResolver;
        }

        /** {@inheritDoc} */
        public void registerResourceResolverForScheme(String scheme,
                ResourceResolver resourceResolver) {
            schemeHandlingResourceResolvers.put(scheme, resourceResolver);
        }

        /** {@inheritDoc} */
        public ResourceResolver build() {
            return new SchemeAwareResourceResolver(
                    Collections.unmodifiableMap(schemeHandlingResourceResolvers), defaultResolver);
        }

    }

    private static final class SchemeAwareResourceResolverBuilderImpl
            implements SchemeAwareResourceResolverBuilder {

        private SchemeAwareResourceResolverBuilder delegate;

        private SchemeAwareResourceResolverBuilderImpl(ResourceResolver defaultResolver) {
            this.delegate = new ActiveSchemeAwareResourceResolverBuilder(defaultResolver);
        }

        /** {@inheritDoc} */
        public void registerResourceResolverForScheme(String scheme,
                ResourceResolver resourceResolver) {
            delegate.registerResourceResolverForScheme(scheme, resourceResolver);
        }

        /** {@inheritDoc} */
        public ResourceResolver build() {
            ResourceResolver resourceResolver = delegate.build();
            delegate = CompletedSchemeAwareResourceResolverBuilder.INSTANCE;
            return resourceResolver;
        }
    }
}
