/*******************************************************************************
 * Copyright (c) 2001, 2008 Oracle Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     Oracle Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.jst.jsf.core.internal;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.content.IContentType;
import org.eclipse.jst.jsf.common.internal.policy.CanonicallyOrderedIteratorPolicy;
import org.eclipse.jst.jsf.common.internal.policy.IIteratorPolicy;
import org.eclipse.jst.jsf.common.internal.policy.IdentifierOrderedIteratorPolicy;
import org.eclipse.jst.jsf.common.internal.strategy.AbstractIdentifiableStrategy;
import org.eclipse.jst.jsf.common.internal.strategy.IIdentifiableStrategy;
import org.eclipse.jst.jsf.common.internal.strategy.IteratorPolicyBasedStrategyComposite;
import org.eclipse.jst.jsf.designtime.internal.view.model.ITagRegistry;
import org.eclipse.jst.jsf.designtime.internal.view.model.TagRegistryFactory.TagRegistryFactoryException;

/**
 * Employs a policy-based strategy to construct a TagRegistry for a particular
 * content-type in a particular project.
 * 
 * @author cbateman
 * 
 */
public final class CompositeTagRegistryFactory
{
    private static CompositeTagRegistryFactory INSTANCE;

    private static ITagRegistryFactoryProvider   TEST_PROVIDER;
    /**
     * For JUNIT TEST ONLY!!!!!
     * @param factoryProvider
     */
    public synchronized void setTestInjectedProvider(final ITagRegistryFactoryProvider factoryProvider)
    {
        TEST_PROVIDER = factoryProvider;
        // TODO: this is risky
        _cachedExtensionsByType.clear();
    }

    /**
     * @return the single instance of the registry factory
     */
    public static synchronized CompositeTagRegistryFactory getInstance()
    {
        if (INSTANCE == null)
        {
            INSTANCE = new CompositeTagRegistryFactory();
        }
        return INSTANCE;
    }

    private final Map<IContentType, Set<ITagRegistryFactoryInfo>> _cachedExtensionsByType =
        new HashMap<IContentType, Set<ITagRegistryFactoryInfo>>(4);

    private CompositeTagRegistryFactory()
    {
        // singleton: no external instantiation
    }

    
    /**
     * @param id
     * @return a tag registry for the id or null if there isn't one.
     */
    public final ITagRegistry getRegistry(final TagRegistryIdentifier id)
    {
        final Set<ITagRegistryFactoryInfo> handlers = getAllTagRegistryFactories();

        final Set<ITagRegistryFactoryInfo> matchingHandlers = findMatchingExtensions(
                id, handlers);

        if (matchingHandlers.size() > 0)
        {
            // optimize: if there is only one handler, no need for strategy
            if (matchingHandlers.size() == 1)
            {
                try
                {
                    return matchingHandlers.iterator().next().getTagRegistryFactory()
                            .createTagRegistry(id.getProject());
                }
                catch (TagRegistryFactoryException e)
                {
                    JSFCorePlugin.log(e, "While trying to acquire a registry"); //$NON-NLS-1$
                }
            }
            else
            {
                // for now, we will order by the canonical name of the extension
                // id in ascending order. Later, we may make this preference
                // based.
                final TagRegistrySelectionStrategy selectionStrategy = new TagRegistrySelectionStrategy(
                        new CanonicallyOrderedIteratorPolicy<String>());

                for (final Iterator<ITagRegistryFactoryInfo> it = matchingHandlers
                        .iterator(); it.hasNext();)
                {
                    selectionStrategy.addStrategy(it.next().getTagRegistryFactory());
                }
                return selectionStrategy.perform(id.getProject());
            }
        }

        return null;
    }

    /**
     * @return get all tag registry factories
     */
    public Set<ITagRegistryFactoryInfo> getAllTagRegistryFactories()
    {
        List<String>  selectionOrder = new ArrayList<String>();
        selectionOrder.add("testInjection"); //$NON-NLS-1$
        selectionOrder.add("extensionPointInjection"); //$NON-NLS-1$
        selectionOrder.add("platformDefault"); //$NON-NLS-1$

        IdentifierOrderedIteratorPolicy<String> policy = new IdentifierOrderedIteratorPolicy<String>(selectionOrder);
        // ignore iterator values that don't exist in the list of possible selections.
        policy.setExcludeNonExplicitValues(true);
        final TagRegistryFactoryProviderSelectionStrategy providerSelector
            = new TagRegistryFactoryProviderSelectionStrategy(policy);
        providerSelector.addStrategy(
          new AbstractIdentifiableStrategy<IProject, ITagRegistryFactoryProvider, String>("testInjection", "FIXME: not for display", null) //$NON-NLS-1$ //$NON-NLS-2$
        {
            @Override
            public ITagRegistryFactoryProvider perform(IProject input)
                    throws Exception
            {
                ITagRegistryFactoryProvider injectedProvider = null;
                synchronized(CompositeTagRegistryFactory.class)
                {
                     injectedProvider = TEST_PROVIDER;
                }
                if (injectedProvider != null)
                {
                    final ITagRegistryFactoryProvider useMe = injectedProvider;
                    return new AbstractTagRegistryFactoryProvider()
                    {
                        @Override
                        public Set<ITagRegistryFactoryInfo> getTagRegistryFactories()
                        {
                            return useMe.getTagRegistryFactories();
                        }
                    };
                }
                return null;
            }
            });
        providerSelector.addStrategy(
                new AbstractIdentifiableStrategy<IProject, ITagRegistryFactoryProvider, String>("platformDefault", "FIXME: not for display", null) //$NON-NLS-1$ //$NON-NLS-2$
              {
                  @Override
                  public ITagRegistryFactoryProvider perform(IProject input)
                          throws Exception
                  {
                      return new AbstractTagRegistryFactoryProvider()
                      {
                          @Override
                          public Set<ITagRegistryFactoryInfo> getTagRegistryFactories()
                          {
                              return TagLibraryRegistryLoader.getAllHandlers();
                          }
                      };
                  }
              });

        ITagRegistryFactoryProvider provider = providerSelector.perform(null);
        if (provider != null)
        {
            return provider.getTagRegistryFactories();
        }
        return Collections.emptySet();
    }

    private Set<ITagRegistryFactoryInfo> findMatchingExtensions(
            TagRegistryIdentifier id, Set<ITagRegistryFactoryInfo> handlers)
    {
        Set<ITagRegistryFactoryInfo> matching = _cachedExtensionsByType.get(id
                .getContentType());

        if (matching == null)
        {
            matching = new HashSet<ITagRegistryFactoryInfo>(4);

            for (final ITagRegistryFactoryInfo handler : handlers)
            {
                if (handler.getContentTypes().contains(id.getContentType()))
                {
                    matching.add(handler);
                }
            }

            // if there is nothing matching, just store the empty set and
            // discard
            // the extra memory
            if (matching.size() > 0)
            {
                _cachedExtensionsByType.put(id.getContentType(), matching);
            }
            else
            {
                _cachedExtensionsByType.put(id.getContentType(),
                        Collections.EMPTY_SET);
            }
        }
        return matching;
    }

    /**
     * Identifies a content type/project context in which to request a tag
     * registry.
     * 
     * @author cbateman
     * 
     */
    public final static class TagRegistryIdentifier
    {
        private final IProject     _project;
        private final IContentType _contentType;

        /**
         * @param project
         * @param contentType
         */
        public TagRegistryIdentifier(final IProject project,
                final IContentType contentType)
        {
            _project = project;
            _contentType = contentType;
        }

        /**
         * @return project
         */
        public IProject getProject()
        {
            return _project;
        }

        /**
         * @return content type
         */
        public IContentType getContentType()
        {
            return _contentType;
        }
        
        public boolean equals(final Object o) {
        	if (o instanceof TagRegistryIdentifier) {        	
	        	final TagRegistryIdentifier other = (TagRegistryIdentifier)o;
	        	final int otherProjectHash = other.getProject() != null ? other.getProject().hashCode() : 0;
	        	final int thisProjectHash = getProject() != null ? getProject().hashCode() : 0;
	        	if (otherProjectHash == thisProjectHash &&
	        			other.getContentType().equals(this.getContentType()))
	        		return true;
        	}
        	return false;
        }
        
        public int hashCode() {
        	return (getProject() != null ? getProject().hashCode() : 0) + 7*_contentType.hashCode();
        }

    }

    private static class TagRegistrySelectionStrategy
            extends
            IteratorPolicyBasedStrategyComposite<IProject, ITagRegistry, ITagRegistry, String, IIdentifiableStrategy<IProject, ITagRegistry, String>>
    {
        private static final ITagRegistry NO_RESULT = null;

        protected TagRegistrySelectionStrategy(IIteratorPolicy<String> policy)
        {
            super(policy);
        }

        @Override
        public ITagRegistry getNoResult()
        {
            return NO_RESULT;
        }
    }
    
    private static class TagRegistryFactoryProviderSelectionStrategy
            extends
            IteratorPolicyBasedStrategyComposite<IProject, ITagRegistryFactoryProvider, ITagRegistryFactoryProvider, String, IIdentifiableStrategy<IProject, ITagRegistryFactoryProvider, String>>
    {
        protected TagRegistryFactoryProviderSelectionStrategy(
                IIteratorPolicy<String> policy)
        {
            super(policy);
        }

        private static final ITagRegistryFactoryProvider NO_RESULT = null;

        @Override
        public ITagRegistryFactoryProvider getNoResult()
        {
            return NO_RESULT;
        }
    }
}
