/*******************************************************************************
 * Copyright (c) 2007 BEA Systems, Inc. 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:
 * BEA Systems, Inc. - initial API and implementation
 *******************************************************************************/
package org.eclipse.jst.j2ee.classpathdep;

import java.util.HashMap;
import java.util.Map;

import org.eclipse.core.commands.ExecutionException;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.jdt.core.IClasspathAttribute;
import org.eclipse.jdt.core.IClasspathEntry;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jst.j2ee.internal.classpathdep.UpdateClasspathAttributesDataModelProperties;
import org.eclipse.jst.j2ee.internal.classpathdep.UpdateClasspathAttributesDataModelProvider;
import org.eclipse.wst.common.frameworks.datamodel.DataModelFactory;
import org.eclipse.wst.common.frameworks.datamodel.IDataModel;
import org.eclipse.wst.common.frameworks.datamodel.IDataModelOperation;

/**
 * Contains utility code for executing the UpdateClasspathAttributeOperation.
 * @since 3.0
 */
public class UpdateClasspathAttributeUtil implements IClasspathDependencyConstants {

	/**
	 * Creates an IClasspathAttribute with the special WTP "org.eclipse.jst.component.dependency" name whose runtime path
	 * (represented by the value) is unspecified and will therefore take the default value for the project in which it is
	 * added. 
	 * @return The created IClasspathAttribute.
	 * @throws CoreException Thrown if a problem is encountered.
	 */
	public static IClasspathAttribute createDependencyAttribute() throws CoreException {
		return createDependencyAttribute("");
	}
	
	/**
	 * Creates an IClasspathAttribute with the special WTP "org.eclipse.jst.component.dependency" name whose runtime path
	 * (represented by the value) is set to the default for either a web project (/WEB-INF/lib) or non-web project (../).
	 * @param isWebApp True if this attribute is being created for a classpath entry on a dynamic web project.
	 * @param isClassFolder True if this attribute is being created for a class folder.
	 * @return The created IClasspathAttribute.
	 * @throws CoreException Thrown if a problem is encountered.
	 */
	public static IClasspathAttribute createDependencyAttribute(final boolean isWebApp, final boolean isClassFolder) throws CoreException {
		return createDependencyAttribute(ClasspathDependencyUtil.getDefaultRuntimePath(isWebApp, isClassFolder));
	}

	/**
	 * Creates an IClasspathAttribute with the special WTP "org.eclipse.jst.component.dependency" name whose runtime path
	 * (represented by the value) is set to the default for either a web project (/WEB-INF/lib) or non-web project (../).
	 * @param isWebApp True if this attribute is being created for a classpath entry on a dynamic web project.
	 * @return The created IClasspathAttribute.
	 * @throws CoreException Thrown if a problem is encountered.
	 */
	public static IClasspathAttribute createDependencyAttribute(final boolean isWebApp) throws CoreException {
		return createDependencyAttribute(ClasspathDependencyUtil.getDefaultRuntimePath(isWebApp));
	}

	/**
	 * Creates an IClasspathAttribute with the special WTP "org.eclipse.jst.component.dependency" name with the
	 * specified runtime path (will be used to set the attribute value).
	 * @param runtimePath The runtime path in the deployed/exported module where resolved classpath components should
	 * be added. Must be non-null.
	 * @return The created IClasspathAttribute.
	 * @throws CoreException Thrown if a problem is encountered.
	 */
	public static IClasspathAttribute createDependencyAttribute(final IPath runtimePath) throws CoreException {
		return createDependencyAttribute(runtimePath.toString());
	}
	
	private static IClasspathAttribute createDependencyAttribute(final String runtimePath) throws CoreException {
		return JavaCore.newClasspathAttribute(IClasspathDependencyConstants.CLASSPATH_COMPONENT_DEPENDENCY, runtimePath);
	}
	
	/**
	 * Creates an IClasspathAttribute with the special WTP "org.eclipse.jst.component.nondependency" name. This attribute is
	 * used on the resolved entries of classpath containers to prevent them from being exported/published.
	 * @return The created IClasspathAttribute.
	 * @throws CoreException Thrown if a problem is encountered.
	 */
	public static IClasspathAttribute createNonDependencyAttribute() throws CoreException {
		return JavaCore.newClasspathAttribute(IClasspathDependencyConstants.CLASSPATH_COMPONENT_NON_DEPENDENCY, "");
	}
	
	/**
	 * Updates the specified Java project so that only the specified classpath entries have
	 * the WTP component dependency attribute.
	 * @param projectName Name of the target Java project.
	 * @param entryToRuntimePath Map from IClasspathEntry to runtime path for all entries that should 
	 * have the component dependency attribute.
	 * @return Status from the operation.
	 * @throws ExecutionException Thrown if an error is encountered.
	 */	
	public static IStatus updateDependencyAttributes(final IProgressMonitor monitor, final String projectName, final Map entryToRuntimePath) 
		throws ExecutionException {
		return createUpdateDependencyAttributesOperation(projectName, entryToRuntimePath).execute(monitor, null);
	}
	
	/**
	 * Creates the IDataModelOperation that will update the classpath for the specified Java project so that
	 * only the specified list of classpath entries will have WTP component dependency attribute. 
	 * @param projectName Name of the target Java project.
	 * @param entryToRuntimePath Map from IClasspathEntry to runtime path for all entries that should 
	 * have the component dependency attribute.
	 * @return The operation.
	 */
	public static IDataModelOperation createUpdateDependencyAttributesOperation(final String projectName, final Map entryToRuntimePath) {
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_WITH_ATTRIBUTE, true);
	}
	
	/**
	 * Creates the IDataModelOperation that will update the classpath for the specified Java project so that
	 * the WTP component dependency attribute will be added to the specified list of classpath entries. 
	 * @param projectName Name of the target Java project.
	 * @param entryToRuntimePath Map from IClasspathEntry to runtime path for all entries that should have the attribute added.
	 * @return The operation.
	 */
	public static IDataModelOperation createAddDependencyAttributesOperation(final String projectName, final Map entryToRuntimePath) {
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_TO_ADD_ATTRIBUTE, true);
	}
	
	/**
	 * Creates the IDataModelOperation that will update the classpath for the specified Java project so that
	 * the WTP component dependency attribute will be removed from the specified list of classpath entries. 
	 * @param projectName Name of the target Java project.
	 * @param entryToRuntimePath Map from IClasspathEntry to runtime path for all entries that should have the attribute removed.
	 * @return The operation.
	 */
	public static IDataModelOperation createRemoveDependencyAttributesOperation(final String projectName, final Map entryToRuntimePath) {
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_TO_REMOVE_ATTRIBUTE, true);
	}
	
	/**
	 * Adds the WTP component dependency attribute to the specified classpath entry using the default runtime path for the project. Does NOT check that the
	 * specified entry is a valid entry for the dependency attribute.
	 * 
	 * @param monitor Progress monitor. Can be null.
	 * @param projectName Name of the target Java project.
	 * @param entry Classpath entry to which the attribute should be added.
	 * @return Status from the operation.
	 * @throws ExecutionException Thrown if an error is encountered.
	 */	
	public static IStatus addDependencyAttribute(final IProgressMonitor monitor, final String projectName, final IClasspathEntry entry) 
		throws ExecutionException {
		return addDependencyAttribute(monitor, projectName, entry, null);
	}
	
	/**
	 * Adds the WTP component non-dependency attribute to the specified classpath entry using the default runtime path for the project. 
	 * 
	 * @param monitor Progress monitor. Can be null.
	 * @param projectName Name of the target Java project.
	 * @param entry Classpath entry to which the attribute should be added.
	 * @return Status from the operation.
	 * @throws ExecutionException Thrown if an error is encountered.
	 */	
	public static IStatus addNonDependencyAttribute(final IProgressMonitor monitor, final String projectName, final IClasspathEntry entry) 
		throws ExecutionException {
		final Map entryToRuntimePath = new HashMap();
		entryToRuntimePath.put(entry, null);
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_TO_ADD_ATTRIBUTE, false).execute(monitor, null);
	}
	
	/**
	 * Adds the WTP component dependency attribute to the specified classpath entry. Does NOT check that the
	 * specified entry is a valid entry for the dependency attribute.
	 * 
	 * @param monitor Progress monitor. Can be null.
	 * @param projectName Name of the target Java project.
	 * @param entry Classpath entry to which the attribute should be added.
	 * @param runtimePath Runtime path to which entry elements should be deployed. Null if the default runtime path for the project should be used.
	 * @return Status from the operation.
	 * @throws ExecutionException Thrown if an error is encountered.
	 */	
	public static IStatus addDependencyAttribute(final IProgressMonitor monitor, final String projectName, final IClasspathEntry entry, final IPath runtimePath) 
		throws ExecutionException {
		final Map entryToRuntimePath = new HashMap();
		entryToRuntimePath.put(entry, runtimePath);
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_TO_ADD_ATTRIBUTE, true).execute(monitor, null);
	}
	
	/**
	 * Removes the WTP component dependency attribute from the specified classpath entry. Does NOT check that the
	 * specified entry is a valid entry for the dependency attribute.
	 * 
	 * @param monitor Progress monitor. Can be null.
	 * @param projectName Name of the target Java project.
	 * @param entry Classpath entry from which the attribute should be removed.
	 * @return Status from the operation.
	 * @throws ExecutionException Thrown if an error is encountered.
	 */	
	public static IStatus removeDependencyAttribute(final IProgressMonitor monitor, final String projectName, final IClasspathEntry entry) 
	throws ExecutionException {
		final Map entryToRuntimePath = new HashMap();
		entryToRuntimePath.put(entry, null);
		return createOperation(projectName, entryToRuntimePath, UpdateClasspathAttributesDataModelProperties.ENTRIES_TO_REMOVE_ATTRIBUTE, true).execute(monitor, null);
	}
	
	private static IDataModelOperation createOperation(String projectName, final Map entryToRuntimePath, final String entryMapProperty, final boolean modifyComponentClasspathDependency) { 
		IDataModel dataModel = DataModelFactory.createDataModel(new UpdateClasspathAttributesDataModelProvider());
		dataModel.setProperty(UpdateClasspathAttributesDataModelProperties.PROJECT_NAME, projectName);
		dataModel.setProperty(entryMapProperty, entryToRuntimePath);
		dataModel.setProperty(UpdateClasspathAttributesDataModelProperties.MODIFY_CLASSPATH_COMPONENT_DEPENDENCY, new Boolean(modifyComponentClasspathDependency));
		return dataModel.getDefaultOperation();
	}
	
}
