/*******************************************************************************
 * Copyright (c) 2010, 2011 Oracle. 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 - initial API and implementation
 ******************************************************************************/
package org.eclipse.jpt.jpa.core.internal.context.orm;

import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
import org.eclipse.jdt.core.dom.CompilationUnit;
import org.eclipse.jpt.common.core.utility.TextRange;
import org.eclipse.jpt.common.utility.MethodSignature;
import org.eclipse.jpt.common.utility.internal.iterators.EmptyIterator;
import org.eclipse.jpt.common.utility.model.event.StateChangeEvent;
import org.eclipse.jpt.common.utility.model.listener.StateChangeListener;
import org.eclipse.jpt.jpa.core.JpaStructureNode;
import org.eclipse.jpt.jpa.core.context.AccessType;
import org.eclipse.jpt.jpa.core.context.java.JavaAttributeMapping;
import org.eclipse.jpt.jpa.core.context.java.JavaPersistentAttribute;
import org.eclipse.jpt.jpa.core.context.java.JavaPersistentType;
import org.eclipse.jpt.jpa.core.context.orm.OrmPersistentAttribute;
import org.eclipse.jpt.jpa.core.context.orm.OrmPersistentType;
import org.eclipse.jpt.jpa.core.context.orm.OrmReadOnlyPersistentAttribute;
import org.eclipse.jpt.jpa.core.context.orm.OrmStructureNodes;
import org.eclipse.jpt.jpa.core.context.orm.OrmTypeMapping;
import org.eclipse.jpt.jpa.core.internal.resource.java.source.SourceNode;
import org.eclipse.jpt.jpa.core.jpa2.context.java.JavaPersistentAttribute2_0;
import org.eclipse.jpt.jpa.core.jpa2.context.orm.OrmReadOnlyPersistentAttribute2_0;
import org.eclipse.jpt.jpa.core.resource.java.Annotation;
import org.eclipse.jpt.jpa.core.resource.java.JavaResourcePersistentAttribute;
import org.eclipse.jpt.jpa.core.resource.java.JavaResourcePersistentMember;
import org.eclipse.jpt.jpa.core.resource.java.JavaResourcePersistentType;
import org.eclipse.jpt.jpa.core.resource.java.NestableAnnotation;
import org.eclipse.wst.validation.internal.provisional.core.IMessage;
import org.eclipse.wst.validation.internal.provisional.core.IReporter;

/**
 * <em>virtual</em> <code>orm.xml</code> persistent attribute
 */
public class VirtualOrmPersistentAttribute
	extends AbstractOrmXmlContextNode
	implements OrmReadOnlyPersistentAttribute2_0
{
	protected final JavaResourcePersistentAttribute javaResourceAttribute;

	/**
	 * This is an "annotated" Java persistent attribute whose state is
	 * determined by its annotations (just like a "normal" Java attribute).
	 * Its parent is an <code>orm.xml</code> persistent type. This is necessary
	 * because the Java attribute's <em>context</em> is the <code>orm.xml</code>
	 * type (e.g. the Java attribute's default table is the table set in the
	 * <code>orm.xml</code> type, not the Java type).
	 * The {@link #originalJavaAttributeListener} keeps this attribute in sync
	 * with any changes made via the Java context model.
	 */
	protected final JavaPersistentAttribute annotatedJavaAttribute;

	/**
	 * This is the "original" Java persistent attribute corresponding to
	 * {@link #javaResourceAttribute} from the Java context model.
	 * If it is found (it can be <code>null</code> if the <code>orm.xml</code>
	 * access type differs from the Java access type), we need to listen to it
	 * for changes so we can refresh our "local" Java attributes (since the
	 * Java resource model does not fire change events, and trigger a
	 * <em>sync</em>, when it is modified by the Java context model - if there
	 * is no Java context attribute, the Java resource model can only be
	 * modified via source code editing and we will <em>sync</em> appropriately).
	 */
	protected JavaPersistentAttribute originalJavaAttribute;
	protected StateChangeListener originalJavaAttributeListener;

	/**
	 * This is a simulated "unannotated" Java persistent attribute. It is built
	 * only if necessary (i.e. when the <code>orm.xml</code> persistent type
	 * has been tagged <em>metadata complete</em>). Like
	 * {@link #annotatedJavaAttribute}, its parent is an
	 * <code>orm.xml</code> persistent type.
	 * The {@link #originalJavaAttributeListener} keeps this attribute in sync
	 * with any changes made via the Java context model.
	 */
	protected JavaPersistentAttribute unannotatedJavaAttribute;

	protected JavaAttributeMapping mapping;  // never null


	public VirtualOrmPersistentAttribute(OrmPersistentType parent, JavaResourcePersistentAttribute javaResourceAttribute) {
		super(parent);
		this.javaResourceAttribute = javaResourceAttribute;
		this.annotatedJavaAttribute = this.buildAnnotatedJavaAttribute();
		this.mapping = this.buildMapping();
	}


	// ********** synchronize/update **********

	@Override
	public void synchronizeWithResourceModel() {
		super.synchronizeWithResourceModel();
		this.syncLocalJavaAttributes();
		// 'mapping' belongs to one of the "local" Java persistent attributes
	}

	@Override
	public void update() {
		super.update();
		this.updateOriginalJavaAttribute();
		this.updateLocalJavaAttributes();
		this.setMapping(this.buildMapping());
	}


	// ********** mapping **********

	public JavaAttributeMapping getMapping() {
		return this.mapping;
	}

	protected void setMapping(JavaAttributeMapping mapping) {
		JavaAttributeMapping old = this.mapping;
		this.mapping = mapping;
		this.firePropertyChanged(DEFAULT_MAPPING_KEY_PROPERTY, old, mapping);
	}

	protected JavaAttributeMapping buildMapping() {
		return this.getJavaPersistentAttribute().getMapping();
	}

	public String getMappingKey() {
		return this.mapping.getKey();
	}

	public String getDefaultMappingKey() {
		return this.mapping.getKey();
	}


	// ********** name **********

	public String getName() {
		return this.mapping.getName();
	}


	// ********** Java persistent attribute **********

	public JavaPersistentAttribute getJavaPersistentAttribute() {
		return this.getOwningTypeMapping().isMetadataComplete() ?
				this.getUnannotatedJavaAttribute() :
				this.annotatedJavaAttribute;
	}

	public JavaPersistentAttribute resolveJavaPersistentAttribute() {
		JavaPersistentType javaType = this.getOwningPersistentType().getJavaPersistentType();
		return (javaType == null) ? null : javaType.getAttributeFor(this.javaResourceAttribute);
	}

	protected JavaPersistentAttribute2_0 getJavaPersistentAttribute2_0() {
		return (JavaPersistentAttribute2_0) this.getJavaPersistentAttribute();
	}

	protected JavaPersistentAttribute buildAnnotatedJavaAttribute() {
		return this.buildJavaAttribute(this.javaResourceAttribute);
	}

	protected JavaPersistentAttribute getUnannotatedJavaAttribute() {
		if (this.unannotatedJavaAttribute == null) {
			this.unannotatedJavaAttribute = this.buildUnannotatedJavaAttribute();
		}
		return this.unannotatedJavaAttribute;
	}

	protected JavaPersistentAttribute buildUnannotatedJavaAttribute() {
		return this.buildJavaAttribute(this.buildUnannotatedJavaResourceAttribute());
	}

	/**
	 * Build a Java resource attribute that wraps the original Java resource
	 * attribute and behaves as though it has no annotations. This will cause
	 * all the settings in the Java <em>context</em> attribute to default.
	 */
	protected JavaResourcePersistentAttribute buildUnannotatedJavaResourceAttribute() {
		return new UnannotatedJavaResourcePersistentAttribute(this.javaResourceAttribute);
	}

	protected JavaPersistentAttribute buildJavaAttribute(JavaResourcePersistentAttribute jrpa) {
		// pass in the orm persistent type as the parent...
		return this.getJpaFactory().buildJavaPersistentAttribute(this.getOwningPersistentType(), jrpa);
	}

	protected void syncLocalJavaAttributes() {
		this.annotatedJavaAttribute.synchronizeWithResourceModel();
		if (this.unannotatedJavaAttribute != null) {
			this.unannotatedJavaAttribute.synchronizeWithResourceModel();
		}
	}

	protected void updateLocalJavaAttributes() {
		this.annotatedJavaAttribute.update();
		if (this.unannotatedJavaAttribute != null) {
			this.unannotatedJavaAttribute.update();
		}
	}

	public JavaResourcePersistentAttribute getJavaResourcePersistentAttribute() {
		return this.javaResourceAttribute;
	}


	// ********** original Java persistent attribute **********

	protected void updateOriginalJavaAttribute() {
		JavaPersistentAttribute newJavaAttribute = this.resolveJavaPersistentAttribute();
		if (newJavaAttribute != this.originalJavaAttribute) {
			if (newJavaAttribute == null) {
				this.originalJavaAttribute.removeStateChangeListener(this.getOriginalJavaAttributeListener());
				this.originalJavaAttribute = null;
			} else {
				if (this.originalJavaAttribute != null) {
					this.originalJavaAttribute.removeStateChangeListener(this.getOriginalJavaAttributeListener());
				}
				this.originalJavaAttribute = newJavaAttribute;
				this.originalJavaAttribute.addStateChangeListener(this.getOriginalJavaAttributeListener());
			}
		}
	}

	protected StateChangeListener getOriginalJavaAttributeListener() {
		if (this.originalJavaAttributeListener == null) {
			this.originalJavaAttributeListener = this.buildOriginalJavaAttributeListener();
		}
		return this.originalJavaAttributeListener;
	}

	protected StateChangeListener buildOriginalJavaAttributeListener() {
		return new StateChangeListener() {
			public void stateChanged(StateChangeEvent event) {
				VirtualOrmPersistentAttribute.this.originalJavaAttributeChanged();
			}
		};
	}

	/**
	 * If the "original" Java persistent attribute (or any of its parts) changes
	 * we need to sync our "local" Java persistent attributes with any possible
	 * changes to the Java resource model. This is necessary for when the Java
	 * context model is modifying the Java resource model, but is redundant when
	 * the Java resource model is triggering a <em>sync</em>.
	 */
	protected void originalJavaAttributeChanged() {
		this.syncLocalJavaAttributes();
	}


	// ********** access **********

	public AccessType getAccess() {
		return this.getJavaPersistentAttribute().getAccess();
	}


	// ********** specified/default **********

	public boolean isVirtual() {
		return true;
	}

	public OrmReadOnlyPersistentAttribute convertToVirtual() {
		throw new UnsupportedOperationException();
	}

	public OrmPersistentAttribute convertToSpecified() {
		if (this.mapping.getKey() == null) {
			throw new IllegalStateException("Use convertToSpecified(String) instead and specify a mapping type"); //$NON-NLS-1$
		}
		return this.getOwningPersistentType().convertAttributeToSpecified(this);
	}

	public OrmPersistentAttribute convertToSpecified(String mappingKey) {
		return this.getOwningPersistentType().convertAttributeToSpecified(this, mappingKey);
	}


	// ********** JpaStructureNode implementation **********

	public String getId() {
		return OrmStructureNodes.PERSISTENT_ATTRIBUTE_ID;
	}

	public JpaStructureNode getStructureNode(int offset) {
		return this;
	}

	public boolean contains(int textOffset) {
		return false;
	}

	public TextRange getSelectionTextRange() {
		return null;
	}

	public void dispose() {
		if (this.originalJavaAttribute != null) {
			this.originalJavaAttribute.removeStateChangeListener(this.getOriginalJavaAttributeListener());
		}
	}


	// ********** validation **********

	@Override
	public void validate(List<IMessage> messages, IReporter reporter) {
		super.validate(messages, reporter);
		// the Java attribute should not need an AST for validation from here
		this.getJavaPersistentAttribute().validate(messages, reporter, null);
	}

	public TextRange getValidationTextRange() {
		return this.getOwningTypeMapping().getAttributesTextRange();
	}


	// ********** metamodel **********

	public String getMetamodelContainerFieldTypeName() {
		return this.getJavaPersistentAttribute2_0().getMetamodelContainerFieldTypeName();
	}

	public String getMetamodelContainerFieldMapKeyTypeName() {
		return this.getJavaPersistentAttribute2_0().getMetamodelContainerFieldMapKeyTypeName();
	}

	public String getMetamodelTypeName() {
		return this.getJavaPersistentAttribute2_0().getMetamodelTypeName();
	}


	// ********** misc **********

	@Override
	public OrmPersistentType getParent() {
		return (OrmPersistentType) super.getParent();
	}

	public OrmPersistentType getOwningPersistentType() {
		return this.getParent();
	}

	public OrmTypeMapping getOwningTypeMapping() {
		return this.getOwningPersistentType().getMapping();
	}

	public String getPrimaryKeyColumnName() {
		return this.mapping.getPrimaryKeyColumnName();
	}

	public String getTypeName() {
		return this.getJavaPersistentAttribute().getTypeName();
	}

	@Override
	public void toString(StringBuilder sb) {
		sb.append(this.getName());
	}


	// ********** unannotated Java resource persistent member **********

	/**
	 * Wrap another Java resource member and suppress all its annotations.
	 */
	protected abstract class UnannotatedJavaResourcePersistentMember<M extends JavaResourcePersistentMember>
		extends SourceNode
		implements JavaResourcePersistentMember
	{
		protected final M member;

		/**
		 * these are built as needed
		 */
		protected final HashMap<String, Annotation> nullAnnotationsCache = new HashMap<String, Annotation>();


		protected UnannotatedJavaResourcePersistentMember(M member) {
			super(member.getParent());
			this.member = member;
		}

		public void initialize(CompilationUnit astRoot) {
			// NOP
		}

		public void synchronizeWith(CompilationUnit astRoot) {
			// NOP
		}


		// ********** annotations **********

		public Iterator<Annotation> annotations() {
			return EmptyIterator.instance();
		}

		public int annotationsSize() {
			return 0;
		}

		public Annotation getAnnotation(String annotationName) {
			return null;
		}

		public synchronized Annotation getNonNullAnnotation(String annotationName) {
			Annotation annotation = this.nullAnnotationsCache.get(annotationName);
			if (annotation == null) {
				annotation = this.buildNullAnnotation(annotationName);
				this.nullAnnotationsCache.put(annotationName, annotation);
			}
			return annotation;
		}

		protected abstract Annotation buildNullAnnotation(String annotationName);

		public Iterator<NestableAnnotation> annotations(String nestableAnnotationName, String containerAnnotationName) {
			return EmptyIterator.instance();
		}

		public Annotation addAnnotation(String annotationName) {
			throw new UnsupportedOperationException();
		}

		public NestableAnnotation addAnnotation(int index, String nestableAnnotationName, String containerAnnotationName) {
			throw new UnsupportedOperationException();
		}

		public void moveAnnotation(int targetIndex, int sourceIndex, String containerAnnotationName) {
			throw new UnsupportedOperationException();
		}

		public void removeAnnotation(String annotationName) {
			throw new UnsupportedOperationException();
		}

		public void removeAnnotation(int index, String nestableAnnotationName, String containerAnnotationName) {
			throw new UnsupportedOperationException();
		}

		public Annotation setPrimaryAnnotation(String primaryAnnotationName, Iterable<String> supportingAnnotationNames) {
			throw new UnsupportedOperationException();
		}

		public void addStandAloneAnnotation(NestableAnnotation standAloneAnnotation) {
			throw new UnsupportedOperationException();
		}


		// ********** persistable **********

		public boolean isPersistable() {
			return this.member.isPersistable();
		}


		// ********** misc **********

		public boolean isAnnotated() {
			return false;
		}

		public boolean isFinal() {
			return this.member.isFinal();
		}

		public boolean isFor(String memberName, int occurrence) {
			return this.member.isFor(memberName, occurrence);
		}

		public TextRange getTextRange(CompilationUnit astRoot) {
			// should never be null
			return this.member.getTextRange(astRoot);
		}

		public TextRange getNameTextRange(CompilationUnit astRoot) {
			// should never be null
			return this.member.getNameTextRange(astRoot);
		}

		public void resolveTypes(CompilationUnit astRoot) {
			// NOP
		}
	}


	// ********** unannotated Java resource persistent member **********

	protected class UnannotatedJavaResourcePersistentAttribute
		extends UnannotatedJavaResourcePersistentMember<JavaResourcePersistentAttribute>
		implements JavaResourcePersistentAttribute
	{
		protected UnannotatedJavaResourcePersistentAttribute(JavaResourcePersistentAttribute attribute){
			super(attribute);
		}


		// ********** annotations **********

		@Override
		public Annotation buildNullAnnotation(String annotationName) {
			return (annotationName == null) ? null : this.buildNullAnnotation_(annotationName);
		}

		private Annotation buildNullAnnotation_(String annotationName) {
			return this.getAnnotationProvider().buildNullAttributeAnnotation(this, annotationName);
		}


		// ********** delegated behavior **********

		@Override
		public JavaResourcePersistentType getParent() {
			return this.member.getParent();
		}

		public JavaResourcePersistentType getResourcePersistentType() {
			return this.member.getResourcePersistentType();
		}

		public String getName() {
			return this.member.getName();
		}

		public boolean isFor(MethodSignature signature, int occurrence) {
			return this.member.isFor(signature, occurrence);
		}

		public boolean isField() {
			return this.member.isField();
		}

		public boolean isProperty() {
			return this.member.isProperty();
		}

		public org.eclipse.jpt.jpa.core.resource.java.AccessType getSpecifiedAccess() {
			return null;
		}

		public boolean typeIsSubTypeOf(String tn) {
			return this.member.typeIsSubTypeOf(tn);
		}

		public boolean typeIsVariablePrimitive() {
			return this.member.typeIsVariablePrimitive();
		}

		public int getModifiers() {
			return this.member.getModifiers();
		}

		public String getTypeName() {
			return this.member.getTypeName();
		}

		public boolean typeIsInterface() {
			return this.member.typeIsInterface();
		}

		public boolean typeIsEnum() {
			return this.member.typeIsEnum();
		}

		public ListIterator<String> typeSuperclassNames() {
			return this.member.typeSuperclassNames();
		}

		public Iterator<String> typeInterfaceNames() {
			return this.member.typeInterfaceNames();
		}

		public ListIterator<String> typeTypeArgumentNames() {
			return this.member.typeTypeArgumentNames();
		}

		public int typeTypeArgumentNamesSize() {
			return this.member.typeTypeArgumentNamesSize();
		}

		public String getTypeTypeArgumentName(int index) {
			return this.member.getTypeTypeArgumentName(index);
		}

		@Override
		public void toString(StringBuilder sb) {
			sb.append(this.getName());
		}
	}
}
