/*******************************************************************************
 * Copyright (c) 2006, 2008 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.core.internal;

import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.resources.IResourceChangeEvent;
import org.eclipse.core.resources.IResourceChangeListener;
import org.eclipse.core.resources.IResourceDelta;
import org.eclipse.core.resources.IWorkspace;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Preferences.IPropertyChangeListener;
import org.eclipse.core.runtime.Preferences.PropertyChangeEvent;
import org.eclipse.jdt.core.ElementChangedEvent;
import org.eclipse.jdt.core.IElementChangedListener;
import org.eclipse.jdt.core.IJavaElement;
import org.eclipse.jdt.core.IJavaElementDelta;
import org.eclipse.jdt.core.IOpenable;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jpt.core.JpaFile;
import org.eclipse.jpt.core.JpaModel;
import org.eclipse.jpt.core.JpaProject;
import org.eclipse.jpt.core.JptCorePlugin;
import org.eclipse.jpt.core.internal.prefs.JpaPreferenceConstants;
import org.eclipse.jpt.utility.internal.BitTools;
import org.eclipse.jpt.utility.internal.StringTools;
import org.eclipse.wst.common.project.facet.core.FacetedProjectFramework;
import org.eclipse.wst.common.project.facet.core.events.IFacetedProjectEvent;
import org.eclipse.wst.common.project.facet.core.events.IFacetedProjectListener;
import org.eclipse.wst.common.project.facet.core.events.IProjectFacetActionEvent;

/**
 * "Internal" global stuff.
 * Provide access via a singleton.
 * Hold and manage the JPA model (which holds all the JPA projects)
 * and the various global listeners. We attempt to determine whether events
 * are relevant before forwarding them to the JPA model.
 * 
 * Various things that cause us to add or remove a JPA project:
 * - Startup of the Dali plug-in will trigger all the JPA projects to be added
 * 
 * - Project created and facet installed
 *     facet POST_INSTALL
 * - Project facet uninstalled
 *     facet PRE_UNINSTALL
 * 
 * - Project opened
 *     facet PROJECT_MODIFIED
 * - Project closed
 *     facet PROJECT_MODIFIED
 * 
 * - Pre-existing project imported (created and opened)
 *     resource POST_CHANGE -> PROJECT -> CHANGED -> OPEN
 * - Project deleted
 *     resource PRE_DELETE
 * 
 * - Project facet installed by editing the facets settings file directly
 *     facet PROJECT_MODIFIED
 * - Project facet uninstalled by editing the facets settings file directly
 *     facet PROJECT_MODIFIED
 */
public class JpaModelManager {

	/**
	 * The JPA model - null until the plug-in is started.
	 */
	private GenericJpaModel jpaModel;

	/**
	 * Listen for changes to projects and files.
	 */
	private final IResourceChangeListener resourceChangeListener;

	/**
	 * Listen for the JPA facet being added or removed from a project.
	 */
	private final IFacetedProjectListener facetedProjectListener;

	/**
	 * Listen for Java changes and forward them to the JPA model,
	 * which will forward them to the JPA projects.
	 */
	private final IElementChangedListener javaElementChangeListener;

	/**
	 * Listen for changes to the "Default JPA Lib" preference
	 * so we can update the corresponding classpath variable.
	 */
	private final IPropertyChangeListener preferencesListener;


	// ********** singleton **********

	private static final JpaModelManager INSTANCE = new JpaModelManager();

	/**
	 * Return the singleton JPA model manager.
	 */
	public static JpaModelManager instance() {
		return INSTANCE;
	}


	// ********** constructor **********

	/**
	 * Private - ensure single instance.
	 */
	private JpaModelManager() {
		super();
		this.resourceChangeListener = new ResourceChangeListener();
		this.facetedProjectListener = new FacetedProjectListener();
		this.javaElementChangeListener = new JavaElementChangeListener();
		this.preferencesListener = new PreferencesListener();
	}


	// ********** plug-in controlled life-cycle **********

	/**
	 * internal - called by JptCorePlugin
	 */
	public synchronized void start() throws Exception {
		debug("*** START JPA model manager ***");
		try {
			this.jpaModel = new GenericJpaModel();
			ResourcesPlugin.getWorkspace().addResourceChangeListener(this.resourceChangeListener);
			FacetedProjectFramework.addListener(this.facetedProjectListener, IFacetedProjectEvent.Type.values());
			JavaCore.addElementChangedListener(this.javaElementChangeListener);
			JptCorePlugin.instance().getPluginPreferences().addPropertyChangeListener(this.preferencesListener);
		} catch (RuntimeException ex) {
			this.log(ex);
			this.stop();
		}
	}

	/**
	 * internal - called by JptCorePlugin
	 */
	public synchronized void stop() throws Exception {
		debug("*** STOP JPA model manager ***");
		JptCorePlugin.instance().getPluginPreferences().removePropertyChangeListener(this.preferencesListener);
		JavaCore.removeElementChangedListener(this.javaElementChangeListener);
		FacetedProjectFramework.removeListener(this.facetedProjectListener);
		ResourcesPlugin.getWorkspace().removeResourceChangeListener(this.resourceChangeListener);
		this.jpaModel.dispose();
		this.jpaModel = null;
	}


	// ********** API **********

	/**
	 * Return the workspace-wide JPA model.
	 */
	public JpaModel getJpaModel() {
		return this.jpaModel;
	}

	/** 
	 * Return the JPA project corresponding to the specified Eclipse project,
	 * or null if unable to associate the specified project with a
	 * JPA project.
	 */
	public JpaProject getJpaProject(IProject project) throws CoreException {
		return this.jpaModel.getJpaProject(project);
	}

	/**
	 * Return the JPA file corresponding to the specified Eclipse file,
	 * or null if unable to associate the specified file with a JPA file.
	 */
	public JpaFile getJpaFile(IFile file) throws CoreException {
		return this.jpaModel.getJpaFile(file);
	}

	/**
	 * The JPA settings associated with the specified Eclipse project
	 * have changed in such a way as to require the associated
	 * JPA project to be completely rebuilt
	 * (e.g. when the user changes a project's JPA platform).
	 */
	public void rebuildJpaProject(IProject project) {
		this.jpaModel.rebuildJpaProject(project);
	}

	/**
	 * Log the specified status.
	 */
	public void log(IStatus status) {
		JptCorePlugin.log(status);
    }

	/**
	 * Log the specified message.
	 */
	public void log(String msg) {
		JptCorePlugin.log(msg);
    }

	/**
	 * Log the specified exception or error.
	 */
	public void log(Throwable throwable) {
		JptCorePlugin.log(throwable);
	}


	// ********** resource changed **********

	/**
	 * Check for:
	 *   - project close/delete
	 *   - file add/remove
	 */
	/* private */ void resourceChanged(IResourceChangeEvent event) {
		if (! (event.getSource() instanceof IWorkspace)) {
			return;  // this probably shouldn't happen...
		}
		switch (event.getType()){
			case IResourceChangeEvent.PRE_DELETE :  // project-only event
				this.resourcePreDelete(event);
				break;
			case IResourceChangeEvent.POST_CHANGE :
				this.resourcePostChange(event);
				break;
			case IResourceChangeEvent.PRE_CLOSE :  // project-only event
			case IResourceChangeEvent.PRE_BUILD :
			case IResourceChangeEvent.POST_BUILD :
			default :
				break;
		}
	}

	/**
	 * A project is being deleted. Remove its corresponding
	 * JPA project if appropriate.
	 */
	private void resourcePreDelete(IResourceChangeEvent event) {
		debug("Resource (Project) PRE_DELETE: " + event.getResource());
		this.jpaModel.projectPreDelete((IProject) event.getResource());
	}

	/**
	 * A resource has changed somehow.
	 * Check for files being added or removed.
	 * (The JPA project only handles added and removed files here, ignoring
	 * changed files.)
	 */
	private void resourcePostChange(IResourceChangeEvent event) {
		debug("Resource POST_CHANGE");
		this.synchronizeFiles(event.getDelta());
		this.checkForOpenedProjects(event.getDelta());
	}

	private void synchronizeFiles(IResourceDelta delta) {
		IResource resource = delta.getResource();
		switch (resource.getType()) {
			case IResource.ROOT :
				this.synchronizeFiles(delta.getAffectedChildren());  // recurse
				break;
			case IResource.PROJECT :
				this.synchronizeFiles((IProject) resource, delta);
				break;
			case IResource.FILE :
			case IResource.FOLDER :
			default :
				break;
		}
	}

	private void synchronizeFiles(IResourceDelta[] deltas) {
		for (int i = 0; i < deltas.length; i++) {
			this.synchronizeFiles(deltas[i]);  // recurse
		}
	}

	/**
	 * Checked exceptions bite.
	 */
	private void synchronizeFiles(IProject project, IResourceDelta delta) {
		try {
			this.jpaModel.synchronizeFiles(project, delta);
		} catch (CoreException ex) {
			this.log(ex);  // problem traversing the project's resources - not much we can do
		}
	}

	/**
	 * Crawl the specified delta, looking for projects being opened.
	 * Projects being deleted are handled in IResourceChangeEvent.PRE_DELETE.
	 * Projects being closed are handled in IFacetedProjectEvent.Type.PROJECT_MODIFIED.
	 */
	private void checkForOpenedProjects(IResourceDelta delta) {
		IResource resource = delta.getResource();
		switch (resource.getType()) {
			case IResource.ROOT :
				this.checkForOpenedProjects(delta.getAffectedChildren());  // recurse
				break;
			case IResource.PROJECT :
				this.checkForOpenedProject((IProject) resource, delta);
				break;
			case IResource.FILE :
			case IResource.FOLDER :
			default :
				break;
		}
	}

	private void checkForOpenedProjects(IResourceDelta[] deltas) {
		for (int i = 0; i < deltas.length; i++) {
			this.checkForOpenedProjects(deltas[i]);  // recurse
		}
	}

	private void checkForOpenedProject(IProject project, IResourceDelta delta) {
		switch (delta.getKind()) {
			case IResourceDelta.CHANGED : 
				this.checkDeltaFlagsForOpenedProject(project, delta);
				break;
			case IResourceDelta.REMOVED :  // already handled with the PRE_DELETE event
			case IResourceDelta.ADDED :  // all but project rename handled with the facet POST_INSTALL event
				this.checkDeltaFlagsForRenamedProject(project, delta);
				break;
			case IResourceDelta.ADDED_PHANTOM :  // ignore
			case IResourceDelta.REMOVED_PHANTOM :  // ignore
			default :
				break;
		}
	}

	/**
	 * We don't get any events from the Facets Framework when a pre-existing
	 * project is imported, so we need to check for the newly imported project here.
	 * 
	 * This event also occurs when a project is simply opened. Project opening
	 * also triggers a Facet PROJECT_MODIFIED event and that is where we add
	 * the JPA project, not here
	 */
	private void checkDeltaFlagsForOpenedProject(IProject project, IResourceDelta delta) {
		if (BitTools.flagIsSet(delta.getFlags(), IResourceDelta.OPEN) && project.isOpen()) {
			debug("\tProject CHANGED - OPEN: " + project.getName());
			this.jpaModel.checkForTransition(project);
		}
	}
	
	/**
	 * We don't get any events from the Facets Framework when a project is renamed,
	 * so we need to check for the renamed projects here.
	 */
	private void checkDeltaFlagsForRenamedProject(IProject project, IResourceDelta delta) {
		if (BitTools.flagIsSet(delta.getFlags(), IResourceDelta.MOVED_FROM) && project.isOpen()) {
			debug("\tProject ADDED - MOVED_FROM: " + delta.getMovedFromPath());
			this.jpaModel.checkForTransition(project);
		}
	}


	// ********** faceted project changed **********

	/**
	 * Check for:
	 *   - install of JPA facet
	 *   - un-install of JPA facet
	 *   - any other appearance or disappearance of the JPA facet
	 */
	/* private */ void facetedProjectChanged(IFacetedProjectEvent event) {
		switch (event.getType()) {
			case POST_INSTALL :
				this.facetedProjectPostInstall((IProjectFacetActionEvent) event);
				break;
			case PRE_UNINSTALL :
				this.facetedProjectPreUninstall((IProjectFacetActionEvent) event);
				break;
			case PROJECT_MODIFIED :
				this.facetedProjectModified(event.getProject().getProject());
				break;
			default :
				break;
		}
	}

	private void facetedProjectPostInstall(IProjectFacetActionEvent event) {
		debug("Facet POST_INSTALL: " + event.getProjectFacet());
		if (event.getProjectFacet().getId().equals(JptCorePlugin.FACET_ID)) {
			this.jpaModel.jpaFacetedProjectPostInstall(event);
		}
	}

	private void facetedProjectPreUninstall(IProjectFacetActionEvent event) {
		debug("Facet PRE_UNINSTALL: " + event.getProjectFacet());
		if (event.getProjectFacet().getId().equals(JptCorePlugin.FACET_ID)) {
			this.jpaModel.jpaFacetedProjectPreUninstall(event);
		}
	}

	/**
	 * This event is triggered for any change to a faceted project.
	 * We use the event to watch for the following:
	 *   - an open project is closed
	 *   - a closed project is opened
	 *   - one of a project's (facet) metadata files is edited directly
	 */
	private void facetedProjectModified(IProject project) {
		debug("Facet PROJECT_MODIFIED: " + project.getName());
		this.jpaModel.checkForTransition(project);
	}


	// ********** Java element changed **********

	/**
	 * Forward the event to the JPA model.
	 */
	/* private */ void javaElementChanged(ElementChangedEvent event) {
		if (this.eventIndicatesProjectAddedButNotOpen(event)) {
			return;
		}
		this.jpaModel.javaElementChanged(event);
	}

	//209275 - This particular event only causes problems in a clean workspace the first time a JPA project
	//is created through the JPA wizard. The second time a JPA project is created, this event occurs, but 
	//it occurs as the wizard is closing so it does not cause a deadlock.
	private boolean eventIndicatesProjectAddedButNotOpen(ElementChangedEvent event) {
		IJavaElementDelta delta = event.getDelta();
		if (delta.getKind() == IJavaElementDelta.CHANGED) {
			if (delta.getElement().getElementType() == IJavaElement.JAVA_MODEL) {
				IJavaElementDelta[] children = delta.getAffectedChildren();
				if (children.length == 1) {
					IJavaElementDelta childDelta = children[0];
					if (childDelta.getKind() == IJavaElementDelta.ADDED) {
						IJavaElement childElement = childDelta.getElement();
						if (childElement.getElementType() == IJavaElement.JAVA_PROJECT) {
							if (childDelta.getAffectedChildren().length == 0) {
								if (!((IOpenable) childElement).isOpen()) {
									return true;
								}
							}
						}
					}
				}
			}
		}	
		return false;
	}

	// ********** preference changed **********

	/**
	 * When the "Default JPA Lib" preference changes,
	 * update the appropriate JDT Core classpath variable.
	 */
	/* private */ void preferenceChanged(PropertyChangeEvent event) {
		if (event.getProperty() == JpaPreferenceConstants.PREF_DEFAULT_JPA_LIB) {
			try {
				JavaCore.setClasspathVariable("DEFAULT_JPA_LIB", new Path((String) event.getNewValue()), null);
			} catch (JavaModelException ex) {
				this.log(ex);  // not sure what would cause this...
			}
		}
	}


	// ********** resource change listener **********

	/**
	 * Forward the Resource change event back to the JPA model manager.
	 */
	private class ResourceChangeListener implements IResourceChangeListener {
		ResourceChangeListener() {
			super();
		}
		public void resourceChanged(IResourceChangeEvent event) {
			JpaModelManager.this.resourceChanged(event);
		}
		@Override
		public String toString() {
			return StringTools.buildToStringFor(this);
		}
	}


	// ********** faceted project listener **********

	/**
	 * Forward the Faceted project change event back to the JPA model manager.
	 */
	private class FacetedProjectListener implements IFacetedProjectListener {
		FacetedProjectListener() {
			super();
		}
		public void handleEvent(IFacetedProjectEvent event) {
			JpaModelManager.this.facetedProjectChanged(event);
		}
		@Override
		public String toString() {
			return StringTools.buildToStringFor(this);
		}
	}


	// ********** Java element change listener **********

	/**
	 * Forward the Java element change event back to the JPA model manager.
	 */
	private class JavaElementChangeListener implements IElementChangedListener {
		JavaElementChangeListener() {
			super();
		}
		public void elementChanged(ElementChangedEvent event) {
			JpaModelManager.this.javaElementChanged(event);
		}
		@Override
		public String toString() {
			return StringTools.buildToStringFor(this);
		}
	}


	// ********** preferences listener **********

	/**
	 * Forward the Preferences change event back to the JPA model manager.
	 */
	private class PreferencesListener implements IPropertyChangeListener {
		PreferencesListener() {
			super();
		}
		public void propertyChange(PropertyChangeEvent event) {
			JpaModelManager.this.preferenceChanged(event);
		}
		@Override
		public String toString() {
			return StringTools.buildToStringFor(this);
		}
	}


	// ********** debug **********

	// @see JpaModelTests#testDEBUG()
	private static final boolean DEBUG = false;

	private static void debug(String message) {
		if (DEBUG) {
			System.out.println(Thread.currentThread().getName() + ": " + message);
		}
	}

}
