/*******************************************************************************
 * Copyright (c) 2000, 2016 IBM 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
 *
 *******************************************************************************/
package org.eclipse.dltk.internal.core;

import org.eclipse.dltk.core.DLTKCore;
import org.eclipse.dltk.core.IModelElement;
import org.eclipse.dltk.core.IModelStatus;
import org.eclipse.dltk.core.IModelStatusConstants;
import org.eclipse.dltk.core.ISourceModule;
import org.eclipse.dltk.core.ModelException;
import org.eclipse.dltk.internal.core.util.Messages;


/**
 * This operation copies/moves a collection of elements from their current
 * container to a new container, optionally renaming the elements.
 * <p>
 * Notes:
 * <ul>
 * <li>If there is already an element with the same name in the new container,
 * the operation either overwrites or aborts, depending on the collision policy
 * setting. The default setting is abort.
 * 
 * <li>When constructors are copied to a type, the constructors are
 * automatically renamed to the name of the destination type.
 * 
 * <li>When main types are renamed (move within the same parent), the
 * compilation unit and constructors are automatically renamed
 * 
 * <li>The collection of elements being copied must all share the same type of
 * container (for example, must all be type members).
 * 
 * <li>The elements are inserted in the new container in the order given.
 * 
 * <li>The elements can be positioned in the new container - see
 * #setInsertBefore. By default, the elements are inserted based on the default
 * positions as specified in the creation operation for that element type.
 * 
 * <li>This operation can be used to copy and rename elements within the same
 * container.
 * 
 * <li>This operation only copies elements contained within compilation units.
 * </ul>
 * 
 */
public class CopyElementsOperation extends MultiOperation {
	/**
	 * When executed, this operation will copy the given elements to the given
	 * containers. The elements and destination containers must be in the
	 * correct order. If there is > 1 destination, the number of destinations
	 * must be the same as the number of elements being copied/moved/renamed.
	 */
	public CopyElementsOperation(IModelElement[] elementsToCopy, IModelElement[] destContainers, boolean force) {
		super(elementsToCopy, destContainers, force);
	}

	/**
	 * When executed, this operation will copy the given elements to the given
	 * container.
	 */
	public CopyElementsOperation(IModelElement[] elementsToCopy, IModelElement destContainer, boolean force) {
		this(elementsToCopy, new IModelElement[] {
			destContainer
		}, force);
	}

	/**
	 * Returns the <code>String</code> to use as the main task name for
	 * progress monitoring.
	 */
	@Override
	protected String getMainTaskName() {
		return Messages.operation_copyElementProgress;
	}

	/**
	 * Returns the nested operation to use for processing this element
	 */
	protected ModelOperation getNestedOperation(IModelElement element) {
		return null;
	}

	/**
	 * Returns <code>true</code> if this element is the main type of its
	 * compilation unit.
	 */
	protected boolean isRenamingMainType(IModelElement element, IModelElement dest) throws ModelException {
		if ((isRename() || getNewNameFor(element) != null) && dest.getElementType() == IModelElement.SOURCE_MODULE) {
			String typeName = dest.getElementName();
			if (DLTKCore.DEBUG) {
				System.err.println("TODO:Add extension remove code here..."); //$NON-NLS-1$
			}
			// typeName =
			// /*org.eclipse.dltk.internal.core.util.Util.getNameWithoutScriptLikeExtension((*/typeName;//);
			return element.getElementName().equals(typeName) && element.getParent().equals(dest);
		}
		return false;
	}

	/**
	 * Copy/move the element from the source to destination, renaming the
	 * elements as specified, honoring the collision policy.
	 * 
	 * @exception ScriptModelException
	 *                if the operation is unable to be completed
	 */
	@Override
	protected void processElement(IModelElement element) throws ModelException {
		ModelOperation op = getNestedOperation(element);
//		boolean createElementInCUOperation = op instanceof CreateElementInCUOperation;
		if (op == null) {
			return;
		}
		if (DLTKCore.DEBUG) {
			System.err.println("TODO: Add CreateElementInCUOperation"); //$NON-NLS-1$
		}
//		if (createElementInCUOperation) {
//			IModelElement sibling = (IModelElement) this.insertBeforeElements.get(element);
//			if (sibling != null) {
//				((CreateElementInCUOperation) op).setRelativePosition(sibling, CreateElementInCUOperation.INSERT_BEFORE);
//			} else if (isRename()) {
//				IModelElement anchor = resolveRenameAnchor(element);
//				if (anchor != null) {
//					((CreateElementInCUOperation) op).setRelativePosition(anchor, CreateElementInCUOperation.INSERT_AFTER); // insert
//					// after
//					// so
//					// that
//					// the
//					// anchor
//					// is
//					// found
//					// before
//					// when
//					// deleted
//					// below
//				}
//			}
//			String newName = getNewNameFor(element);
//			if (newName != null) {
//				((CreateElementInCUOperation) op).setAlteredName(newName);
//			}
//		}
		executeNestedOperation(op, 1);
		ModelElement destination = (ModelElement) getDestinationParent(element);
		ISourceModule unit = destination.getSourceModule();
		if (!unit.isWorkingCopy()) {
			unit.close();
		}
//		if (createElementInCUOperation && isMove() && !isRenamingMainType(element, destination)) {
//			DeleteElementsOperation deleteOp = new DeleteElementsOperation(new IModelElement[] {
//				element
//			}, this.force);
//			executeNestedOperation(deleteOp, 1);
//		}
	}

	/**
	 * Returns the anchor used for positioning in the destination for the
	 * element being renamed. For renaming, if no anchor has explicitly been
	 * provided, the element is anchored in the same position.
	 */
//	private IModelElement resolveRenameAnchor(IModelElement element) throws ModelException {
//		IParent parent = (IParent) element.getParent();
//		IModelElement[] children = parent.getChildren();
//		for (int i = 0; i < children.length; i++) {
//			IModelElement child = children[i];
//			if (child.equals(element)) {
//				return child;
//			}
//		}
//		return null;
//	}

	/**
	 * Possible failures:
	 * <ul>
	 * <li>NO_ELEMENTS_TO_PROCESS - no elements supplied to the operation
	 * <li>INDEX_OUT_OF_BOUNDS - the number of renamings supplied to the
	 * operation does not match the number of elements that were supplied.
	 * </ul>
	 */
	@Override
	protected IModelStatus verify() {
		IModelStatus status = super.verify();
		if (!status.isOK()) {
			return status;
		}
		if (this.renamingsList != null && this.renamingsList.length != this.elementsToProcess.length) {
			return new ModelStatus(IModelStatusConstants.INDEX_OUT_OF_BOUNDS);
		}
		return ModelStatus.VERIFIED_OK;
	}

	/**
	 * @see MultiOperation
	 * 
	 * Possible failure codes:
	 * <ul>
	 * 
	 * <li>ELEMENT_DOES_NOT_EXIST - <code>element</code> or its specified
	 * destination is is <code>null</code> or does not exist. If a
	 * <code>null</code> element is supplied, no element is provided in the
	 * status, otherwise, the non-existant element is supplied in the status.
	 * <li>INVALID_ELEMENT_TYPES - <code>element</code> is not contained
	 * within a compilation unit. This operation only operates on elements
	 * contained within compilation units.
	 * <li>READ_ONLY - <code>element</code> is read only.
	 * <li>INVALID_DESTINATION - The destination parent specified for
	 * <code>element</code> is of an incompatible type. The destination for a
	 * package declaration or import declaration must be a compilation unit; the
	 * destination for a type must be a type or compilation unit; the destinaion
	 * for any type member (other than a type) must be a type. When this error
	 * occurs, the element provided in the operation status is the
	 * <code>element</code>.
	 * <li>INVALID_NAME - the new name for <code>element</code> does not have
	 * valid syntax. In this case the element and name are provided in the
	 * status.
	 * 
	 * </ul>
	 */
	@Override
	protected void verify(IModelElement element) throws ModelException {
		if (element == null || !element.exists())
			error(IModelStatusConstants.ELEMENT_DOES_NOT_EXIST, element);
		if (element.getElementType() < IModelElement.TYPE)
			error(IModelStatusConstants.INVALID_ELEMENT_TYPES, element);
		if (element.isReadOnly())
			error(IModelStatusConstants.READ_ONLY, element);
		IModelElement dest = getDestinationParent(element);
		verifyDestination(element, dest);
		verifySibling(element, dest);
		if (this.renamingsList != null) {
			verifyRenaming(element);
		}
	}
}
