/*******************************************************************************
 * 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.designtime.internal.view;

import java.util.ArrayList;
import java.util.HashMap;
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.CoreException;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.IType;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jem.internal.proxy.core.IBeanTypeProxy;
import org.eclipse.jem.internal.proxy.core.IConfigurationContributor;
import org.eclipse.jem.internal.proxy.core.IStandardBeanTypeProxyFactory;
import org.eclipse.jem.internal.proxy.core.ProxyFactoryRegistry;
import org.eclipse.jem.internal.proxy.ide.IDERegistration;
import org.eclipse.jst.jsf.common.internal.types.TypeInfoCache;
import org.eclipse.jst.jsf.common.runtime.internal.model.component.ComponentTypeInfo;
import org.eclipse.jst.jsf.common.runtime.internal.model.decorator.ConverterTypeInfo;
import org.eclipse.jst.jsf.common.runtime.internal.model.decorator.ValidatorTypeInfo;
import org.eclipse.jst.jsf.common.util.JDTBeanIntrospector;
import org.eclipse.jst.jsf.common.util.JDTBeanProperty;
import org.eclipse.jst.jsf.core.internal.JSFCorePlugin;
import org.eclipse.jst.jsf.core.internal.JSFCoreTraceOptions;
import org.eclipse.jst.jsf.core.internal.jem.BeanProxyUtil.BeanProxyWrapper;
import org.eclipse.jst.jsf.core.internal.jem.BeanProxyUtil.ProxyException;
import org.eclipse.jst.jsf.core.jsfappconfig.JSFAppConfigManager;
import org.eclipse.jst.jsf.facesconfig.emf.ComponentType;
import org.eclipse.jst.jsf.facesconfig.emf.ConverterType;
import org.eclipse.jst.jsf.facesconfig.emf.ValidatorType;

/**
 * Utility class for finding and bean introspecting component and related
 * classes.
 * 
 * @author cbateman
 * 
 */
public final class DTComponentIntrospector
{
    /**
     * A shared type cache for doing tag class introspection. The cache stores
     * type hierarchies and updates them on detected changes to reduce the
     * overhead of doing such lookups
     */
    private static TypeInfoCache TYPE_CACHE; // lazily created, don't access

    // directly

    /**
     * @return the type cache used by all DTComponentIntrospector internally.
     */
    public static TypeInfoCache getSharedTypeCache()
    {
        if (TYPE_CACHE == null)
        {
            TYPE_CACHE = TypeInfoCache.createNewInstance();
        }
        return TYPE_CACHE;
    }

    /**
     * @param classType
     * @param className
     * @param project
     * @param contributors  may be null
     * @return the component type info for the class type or null if none.  Adds
     * contributors to the class path
     */
    public static ComponentTypeInfo getComponent(final String classType,
            final String className, final IProject project,
            final IConfigurationContributor[] contributors)
    {
        final ProxyFactoryRegistry registry = getProxyFactoryRegistry(project,
                contributors);

        if (registry != null)
        {
            final IStandardBeanTypeProxyFactory factory = registry
                    .getBeanTypeProxyFactory();
            final IBeanTypeProxy classTypeProxy = factory
                    .getBeanTypeProxy(className);
            final BeanProxyWrapper classTypeWrapper = new BeanProxyWrapper(
                    classTypeProxy);

            String family = null;
            String renderer = null;
            try
            {
                classTypeWrapper.init();
                family = classTypeWrapper.callStringMethod("getFamily");
                renderer = classTypeWrapper.callStringMethod("getRendererType");
            }
            catch (ProxyException e1)
            {
                // fall through
                if (JSFCoreTraceOptions.TRACE_JSPTAGINTROSPECTOR)
                {
                    JSFCoreTraceOptions.log("DTComponentIntrospector.getComponent:", e1);
                }
            }

            IType type = null;

            try
            {
                type = JavaCore.create(project).findType(className);
            }
            catch (JavaModelException e)
            {
                // fall through;
            }

            List<String> interfaces = new ArrayList<String>();
            List<String> superClasses = new ArrayList<String>();

            if (type != null)
            {
                TypeInfoCache typeCache = getSharedTypeCache();

                IType[] interfaceTypes = typeCache.cacheInterfaceTypesFor(type);
                for (IType interfaze : interfaceTypes)
                {
                    interfaces.add(interfaze.getFullyQualifiedName());
                }

                IType[] superClassTypes = typeCache.cacheSupertypesFor(type);

                for (IType superClass : superClassTypes)
                {
                    superClasses.add(superClass.getFullyQualifiedName());
                }
            }

            return new ComponentTypeInfo(classType, className, superClasses
                    .toArray(new String[0]), interfaces.toArray(new String[0]),
                    family, renderer);
        }
        return null;
    }

    /**
     * @param classType
     * @param className
     * @param project
     * @return the component type info with no additional classpath
     *         contributions. May return null;
     */
    public static ComponentTypeInfo getComponent(final String classType,
            final String className, final IProject project)
    {
        return getComponent(classType, className, project, null);
    }

    /**
     * @param converterId
     * @param converterClass
     * @return a new converter type info for the converter id.
     */
    public static ConverterTypeInfo getConverter(final String converterId,
            final String converterClass)
    {
        return new ConverterTypeInfo(converterClass, converterId);
    }

    /**
     * @param validatorId
     * @param validatorClass
     * @return a new validator type info for the validator id
     */
    public static ValidatorTypeInfo getValidator(final String validatorId,
            final String validatorClass)
    {
        return new ValidatorTypeInfo(validatorClass, validatorId);
    }

    /**
     * @param componentType
     * @param project
     * @return the configured class name for the JSF component type id or null
     *         if not found.
     */
    public static String findComponentClass(final String componentType,
            final IProject project)
    {
        final JSFAppConfigManager manager = JSFAppConfigManager
                .getInstance(project);
        final List components = manager.getComponents();

        for (final Iterator it = components.iterator(); it.hasNext();)
        {
            final ComponentType component = (ComponentType) it.next();
            final String type = component.getComponentType().getTextContent()
                    .trim();

            if (componentType.equals(type))
            {
                return component.getComponentClass().getTextContent().trim();
            }
        }
        return null;
    }

    /**
     * @param converterId
     * @param project
     * @return a fully qualified class name corresponding to converterId or null
     *         if none.
     */
    public static String findConverterClass(final String converterId,
            final IProject project)
    {
        final JSFAppConfigManager manager = JSFAppConfigManager
                .getInstance(project);
        final List converters = manager.getConverters();

        for (final Iterator it = converters.iterator(); it.hasNext();)
        {
            final ConverterType converter = (ConverterType) it.next();

            if (converter != null && converter.getConverterId() != null
                    && converter.getConverterId().getTextContent() != null)
            {
                final String type = converter.getConverterId().getTextContent()
                        .trim();

                if (converterId.equals(type))
                {
                    if (converter.getConverterClass() != null && converter.getConverterClass().getTextContent()!=null)
                    {
                        return converter.getConverterClass().getTextContent()
                                .trim();
                    }
                    return null;
                }
            }
        }
        return null;
    }

    /**
     * @param validatorId
     * @param project
     * @return a fully qualified class name corresponding to the validatorId or
     *         null if none.
     */
    public static String findValidatorClass(final String validatorId,
            final IProject project)
    {
        final JSFAppConfigManager manager = JSFAppConfigManager
                .getInstance(project);
        final List converters = manager.getValidators();

        for (final Iterator it = converters.iterator(); it.hasNext();)
        {
            final ValidatorType validatorType = (ValidatorType) it.next();
            
            if (validatorType != null && validatorType.getValidatorId() != null && 
                    validatorType.getValidatorId().getTextContent() != null)
            {
                final String type = validatorType.getValidatorId().getTextContent()
                        .trim();
    
                if (validatorId.equals(type))
                {
                    return validatorType.getValidatorClass().getTextContent()
                            .trim();
                }
            }
        }
        return null;
    }

    /**
     * @param type
     * @param checkInstanceOf
     * @return true if type resolves to a type that is an instance of one of the
     *         types in checkInstanceOf.
     */
    public static boolean isTypeNameInstanceOfClass(final IType type,
            final Set<String> checkInstanceOf)
    {
        if (type != null)
        {
            // first and foremost, are these exactly droids you're
            // looking for and not just their predecessors?
            if (checkInstanceOf.contains(type.getFullyQualifiedName()))
            {
                return true;
            }

            for (final IType supertype : getSharedTypeCache()
                    .cacheSupertypesFor(type))
            {
                if (checkInstanceOf.contains(supertype.getFullyQualifiedName()))
                {
                    return true;
                }
            }

            for (final IType interfaces : getSharedTypeCache()
                    .cacheInterfaceTypesFor(type))
            {
                if (checkInstanceOf
                        .contains(interfaces.getFullyQualifiedName()))
                {
                    return true;
                }
            }
        }

        return false;
    }

    /**
     * @param typeInfo
     * @param project
     * @return a list of all bean properties (using the POJO method) on
     *         typeInfo. List may be empty, never null.
     */
    public static Map<String, JDTBeanProperty> getBeanProperties(
            final ComponentTypeInfo typeInfo, final IProject project)
    {
        Map<String, JDTBeanProperty> properties = new HashMap<String, JDTBeanProperty>();

        IJavaProject javaProject = JavaCore.create(project);
        try
        {
            IType type = javaProject.findType(typeInfo.getClassName());

            if (type != null)
            {
                // TODO: should be able to use type cache for this
                final JDTBeanIntrospector introspector = new JDTBeanIntrospector(
                        type);
                properties = introspector.getProperties();
            }
        }
        catch (JavaModelException e)
        {
            JSFCorePlugin.log("Error finding component type", e);
        }

        return properties;
    }

    /**
     * @param project
     * @return a new proxy factory registry or null;
     * 
     * TODO: caching?
     */
    private static ProxyFactoryRegistry getProxyFactoryRegistry(
            final IProject project, final IConfigurationContributor[] contributors)
    {
        try
        {
            return IDERegistration.startAnImplementation(contributors, false, project,
                    project.getName(), JSFCorePlugin.PLUGIN_ID,
                    new NullProgressMonitor());
        }
        catch (final CoreException e)
        {
            JSFCorePlugin.log("Error starting vm for project: "
                    + project.getName(), e);
        }

        return null;
    }

    private DTComponentIntrospector()
    {
        // no external instantiation
    }

    // private static class
}
