/*******************************************************************************
 * Copyright (c) 2009 Shane Clarke.
 * 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:
 *    Shane Clarke - initial API and implementation
 *******************************************************************************/
package org.eclipse.jst.ws.annotations.core;

import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedList;
import java.util.List;

import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IConfigurationElement;
import org.eclipse.jst.ws.annotations.core.initialization.IAnnotationAttributeInitializer;

/**
 * An <code>AnnotationDefinition</code> is a representation of the information contributed through the
 * <code>org.eclipse.jst.ws.annotations.core.annotationDefinition</code>,
 * <code>org.eclipse.jst.ws.annotations.core.annotationCategory</code> and
 * <code>org.eclipse.jst.ws.annotations.core.annotationInitializer</code> extension points.
 * for a <code>java.lang.annotation.Annotation</code> class.
 * <p>
 * It supplies the annotation class name, its annotation category, the applicable targets for the annotation
 * and an <code>IAnnotationAttributeInitializer</code> to initialize the annotations element-value pairs.
 * </p>
 * <strong>Provisional API:</strong> This class/interface is part of an interim API that is still under
 * development and expected to change significantly before reaching stability. It is being made available at
 * this early stage to solicit feedback from pioneering adopters on the understanding that any code that uses
 * this API will almost certainly be broken (repeatedly) as the API evolves.
 * </p>
 */
public final class AnnotationDefinition {
    private static final String ATT_CLASS = "class"; //$NON-NLS-1$
    private static final String ATT_NAME = "name"; //$NON-NLS-1$
    private static final String ATT_RESTRICTED_TO = "restrictedTo"; //$NON-NLS-1$

    private static final String RESTRICTED_TO_CLASS_ONLY = "CLASS_ONLY";
    private static final String RESTRICTED_TO_INTERFACE_ONLY = "INTERFACE_ONLY";
    private static final String RESTRICTED_TO_ENUM_ONLY = "ENUM_ONLY";

	private static final String ELEM_TARGET_FILTER = "targetFilter"; //$NON-NLS-1$
	private static final String ATT_TARGET = "target"; //$NON-NLS-1$

    private IConfigurationElement configurationElement;
    private String category;
    private String annotationClassName;
    private Class<? extends java.lang.annotation.Annotation> annotationClass;
    private List<ElementType> targets;
    private String name;
    private IAnnotationAttributeInitializer annotationInitializer;
    private String restictedTo;
    private boolean interfaceOnly;
    private boolean classOnly;
    private boolean enumOnly;

    /**
     * Constructs an <code>AnnotationDefinition</code> using information from the
     * <code>org.eclipse.jst.ws.annotations.core.annotationDefinition</code> extension point and category name.
     * @param configurationElement the <code>annotation</code> element from the <code>org.eclipse.jst.ws.annotations.core.annotationDefinition</code> extension point
     * @param category the category name
     */
    public AnnotationDefinition(IConfigurationElement configurationElement, String category) {
        this.configurationElement = configurationElement;
        this.category = category;

        this.annotationClassName = AnnotationsManager.getAttributeValue(configurationElement, ATT_CLASS);
        this.name = AnnotationsManager.getAttributeValue(configurationElement, ATT_NAME);
        this.restictedTo = AnnotationsManager.getAttributeValue(configurationElement,
                ATT_RESTRICTED_TO);
        this.classOnly = restictedTo.equals(RESTRICTED_TO_CLASS_ONLY);
        this.interfaceOnly = restictedTo.equals(RESTRICTED_TO_INTERFACE_ONLY);
        this.enumOnly = restictedTo.equals(RESTRICTED_TO_ENUM_ONLY);
    }

    /**
     * Returns the annotation name.
     * @return the annotation name.
     */
    public String getName() {
        return name;
    }

    /**
     * Returns the category the annotation belongs to.
     * @return the annotation category.
     */
    public String getCategory() {
        return category;
    }

    /**
     * Returns the fully qualified class name of the annotation.
     * @return the fully qualified class name of the annotation.
     */
    public String getAnnotationClassName() {
        return annotationClassName;
    }

    /**
     * Returns whether the annotation is restricted to class types.
     * @return <code>true</code> if the annotation is restricted to classes only.
     */
    public boolean isClassOnly() {
        return classOnly;
    }

    /**
     * Returns whether the annotation is restricted to interface types.
     * @return <code>true</code> if the annotation is restricted to interfaces only.
     */
    public boolean isInterfaceOnly() {
        return interfaceOnly;
    }

    /**
     * Returns whether the annotation is restricted to enum types.
     * @return <code>true</code> if the annotation is restricted to enums only.
     */
    public boolean isEnumOnly() {
        return enumOnly;
    }

    /**
     * Returns the annotation class as specified by the <code>class</code> attribute of the
     * <code>annotation<annotation> element in the <code>org.eclipse.jst.ws.annotations.core.annotationDefinition</code>
     * extension point.
     *
     * @return the annotation class
     */
    @SuppressWarnings("unchecked")
    public Class<? extends java.lang.annotation.Annotation> getAnnotationClass() {
        if (annotationClass == null) {
            try {
                Class<?> aClass = Class.forName(annotationClassName);
                if (aClass.isAnnotation()) {
                    annotationClass = (Class<java.lang.annotation.Annotation>)Class.forName(
                            annotationClassName);
                }
            } catch(ClassNotFoundException cnfe) {
                AnnotationsCorePlugin.log(cnfe);
            }
        }
        return annotationClass;
    }

    /**
     * Returns a list of {@link ElementType} that specify the Java elements to which the annotation
     * can be applied.
     * <p>
     * The element types are retrieved from the annotations
     * {@link java.lang.annotation.Target} meta-annotation type. This list can be filtered using
     * the <code>targetFilter</code> element on the
     * <code>org.eclipse.jst.ws.annotations.core.annotationDefinition</code> extension point when defining
     * the annotation.
     * </p>
     * @return a list of element types.
     */
    public List<ElementType> getTargets() {
        if (targets == null) {
        	targets = new LinkedList<ElementType>();

            Class<? extends java.lang.annotation.Annotation> annotation = getAnnotationClass();
            if (annotation != null) {
            	Target target = annotation.getAnnotation(Target.class);
            	if (target != null) {
            	    targets.addAll(Arrays.asList(target.value()));

                    List<ElementType> filteredTargets = getFilteredTargets(configurationElement);
                    if (targets.containsAll(filteredTargets) && filteredTargets.size() < targets.size()) {
                        targets.removeAll(filteredTargets);
                    }
            	}
            }
        }
        return targets;
    }

    /**
     * Returns the annotations attribute initializer as specified in the
     * <code>org.eclipse.jst.ws.annotations.core.annotationInitializer</code> extension point or null if no
     * initializer can be found.
     *
     * @return the <code>IAnnotationAttributeInitializer</code>
     */
    public IAnnotationAttributeInitializer getAnnotationAttributeInitializer() {
        if (annotationInitializer == null) {
            try {
                IConfigurationElement configurationElement =
                    AnnotationsManager.getAnnotationInitializerCache().get(getAnnotationClassName());
                if (configurationElement != null) {
                    annotationInitializer = (IAnnotationAttributeInitializer)configurationElement
                        .createExecutableExtension(ATT_CLASS);
                }
            } catch (CoreException ce) {
                AnnotationsCorePlugin.log(ce.getStatus());
            }
        }
        return annotationInitializer;
    }

	  private List<ElementType> getFilteredTargets(IConfigurationElement configurationElement) {
		  List<ElementType> targets = new ArrayList<ElementType>(7);
		  try {
			  IConfigurationElement[] deprecatedTargets = configurationElement.getChildren(ELEM_TARGET_FILTER);
			  for (IConfigurationElement deprecatedTargetElement : deprecatedTargets) {
				  String target = AnnotationsManager.getAttributeValue(deprecatedTargetElement, ATT_TARGET);
				  targets.add(ElementType.valueOf(target));
			  }
		  } catch (IllegalArgumentException iae) {
			  AnnotationsCorePlugin.log(iae);
		  }
		  return targets;
	  }
}
