/*******************************************************************************
 * Copyright (c) 2001, 2005 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
 *
 * Contributors:
 * IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.jst.j2ee.commonarchivecore.internal.strategy;



import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;

import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.jst.j2ee.commonarchivecore.internal.Archive;
import org.eclipse.jst.j2ee.commonarchivecore.internal.CommonArchiveResourceHandler;
import org.eclipse.jst.j2ee.commonarchivecore.internal.File;
import org.eclipse.jst.j2ee.commonarchivecore.internal.ModuleFile;
import org.eclipse.jst.j2ee.commonarchivecore.internal.exception.SaveFailureException;
import org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.ArchiveManifest;
import org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.FileIterator;
import org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.SaveFilter;
import org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.SaveFilterImpl;
import org.eclipse.jst.j2ee.commonarchivecore.internal.util.ArchiveUtil;
import org.eclipse.jst.j2ee.internal.J2EEConstants;
import org.eclipse.wst.common.internal.emf.resource.CompatibilityXMIResource;
import org.eclipse.wst.common.internal.emf.resource.TranslatorResource;
import org.eclipse.wst.common.internal.emf.utilities.Revisit;


/**
 * Abstract implementer off which any save strategy can subclass
 * 
 * @see com.ibm.etools.archive.SaveStrategy
 */

public abstract class SaveStrategyImpl extends ArchiveStrategyImpl implements SaveStrategy {
	protected SaveFilter filter;

	/**
	 * SaveStrategyImpl constructor comment.
	 */
	public SaveStrategyImpl() {
		super();
	}

	/**
	 * The default is to do nothing - subclasses should override as necessary
	 */
	public void close() throws java.io.IOException {
		//Default
	}

	protected abstract SaveStrategy createNestedSaveStrategy(Archive anArchive) throws java.io.IOException;

	/**
	 * The default is to do nothing - subclasses should override as necessary
	 */
	public void finish() throws java.io.IOException {
		//Default
	}

	/**
	 * Insert the method's description here. Creation date: (02/28/01 4:11:28 PM)
	 * 
	 * @return com.ibm.etools.archive.SaveFilter
	 */
	public org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.SaveFilter getFilter() {
		if (filter == null)
			filter = new SaveFilterImpl();
		return filter;
	}

	protected abstract OutputStream getOutputStreamForResource(Resource aResource) throws java.io.IOException;

	/**
	 * @see com.ibm.etools.archive.SaveStrategy
	 */
	public boolean isDirectory() {
		return false;
	}

	protected boolean isLoadedResourceOrManifest(File aFile) {
		return getArchive().isMofResourceLoaded(aFile.getURI()) || aFile.getURI().equals(J2EEConstants.MANIFEST_URI);
	}

	public void save() throws SaveFailureException {

		saveManifest();
		saveMofResources();
		saveFiles();

	}

	/**
	 * @see com.ibm.etools.archive.SaveStrategy
	 */
	public void save(Archive anArchive) throws SaveFailureException {
		SaveStrategy strat = null;
		try {
			strat = createNestedSaveStrategy(anArchive);
		} catch (java.io.IOException iox) {
			throw new SaveFailureException(anArchive.getURI(), iox);
		}
		anArchive.save(strat);

	}

	/**
	 * @see com.ibm.etools.archive.SaveStrategy
	 */
	public void save(File aFile, FileIterator iterator) throws SaveFailureException {
		if (aFile.isArchive() && shouldIterateOver((Archive) aFile))
			save((Archive) aFile);
		else {
			InputStream in = null;
			if (!aFile.isDirectoryEntry()) {
				try {
					in = iterator.getInputStream(aFile);
				} catch (IOException ex) {
					throw new SaveFailureException(aFile.getURI(), ex);
				}
			}
			save(aFile, in);
		}
	}

	public abstract void save(File aFile, InputStream in) throws SaveFailureException;

	protected void saveFiles() throws SaveFailureException {
		try {
			FileIterator iterator = getArchive().getFilesForSave();
			while (iterator.hasNext()) {
				File aFile = iterator.next();
				if (shouldSave(aFile))
					save(aFile, iterator);
			}
		} catch (IOException iox) {
			throw new SaveFailureException(CommonArchiveResourceHandler.Error_occurred_iterating_f_EXC_, iox); // = "Error occurred iterating files"
		}
	}

	protected void saveManifest() throws SaveFailureException {
		if (!shouldSave(J2EEConstants.MANIFEST_URI))
			return;
		ArchiveManifest mf = getArchive().getManifest();
		if (mf.getManifestVersion() == null || mf.getManifestVersion().equals(""))//$NON-NLS-1$
			mf.setManifestVersion("1.0");//$NON-NLS-1$
		save(mf);
	}

	/**
	 * @see com.ibm.etools.archive.SaveStrategy
	 */
	public void saveMofResource(org.eclipse.emf.ecore.resource.Resource aResource) throws SaveFailureException {
		if (!shouldSave(aResource))
			return;
		setEncoding(aResource);
		try {
			boolean wasModified = aResource.isModified();
			OutputStream os = getOutputStreamForResource(aResource);
			saveMofResource(aResource, os);
			aResource.setModified(wasModified);
		} catch (Exception e) {
			throw new SaveFailureException(aResource.getURI().toString(), e);
		}
	}

	/**
	 * @see com.ibm.etools.archive.SaveStrategy
	 */
	protected void saveMofResource(org.eclipse.emf.ecore.resource.Resource aResource, OutputStream os) throws IOException {
		aResource.save(os, Collections.EMPTY_MAP);
	}

	protected void saveMofResources() throws SaveFailureException {
		Iterator iterator = getArchive().getLoadedMofResources().iterator();
		//We have to go through this process because java resources could get added during the
		//process of iterating and saving, and adding to a collection while iterating causes a
		// failure
		List xmiResources = new ArrayList();
		//We will save the xmi resources first, then the xml resources. This way the
		//any necessary id's for referenced objects will have been generated prior to save
		List xmlResources = new ArrayList();
		Resource res = null;
		while (iterator.hasNext()) {
			res = (Resource) iterator.next();
			//		We don't want to save the java reflection resources or uri mapped resources
			if (!ArchiveUtil.isJavaResource(res) && !ArchiveUtil.isRegisteredURIMapping(res) && !ArchiveUtil.isPlatformMetaResource(res)) {
				Revisit.revisit();
				//For now, always use the mof5 format
				if (res instanceof CompatibilityXMIResource)
					((CompatibilityXMIResource) res).setFormat(CompatibilityXMIResource.FORMAT_MOF5);
				if (res instanceof TranslatorResource)
					xmlResources.add(res);
				else {
					xmiResources.add(res);
				}
			}
		}
		basicSaveMofResources(xmiResources);
		basicSaveMofResources(xmlResources);
	}

	protected void basicSaveMofResources(List resources) throws SaveFailureException {
		Resource res = null;
		for (int i = 0; i < resources.size(); i++) {
			res = (Resource) resources.get(i);
			saveMofResource(res);

		}
	}

	protected void setEncoding(Resource aResource) {
		if (aResource instanceof org.eclipse.emf.ecore.xmi.XMLResource)
			((org.eclipse.emf.ecore.xmi.XMLResource) aResource).setEncoding(archive.getXmlEncoding());
	}

	/**
	 * Insert the method's description here. Creation date: (02/28/01 4:11:28 PM)
	 * 
	 * @param newFilter
	 *            com.ibm.etools.archive.SaveFilter
	 */
	public void setFilter(org.eclipse.jst.j2ee.commonarchivecore.internal.helpers.SaveFilter newFilter) {
		filter = newFilter;
	}

	/**
	 * Answer whether the nested archive needs to be saved one file at a time, or if we can bulk
	 * save it from the original
	 */
	protected boolean shouldIterateOver(Archive anArchive) {
		return anArchive.getLoadStrategy().requiresIterationOnSave();
	}

	protected boolean shouldSave(File aFile) {
		boolean loaded = isLoadedResourceOrManifest(aFile);
		if (loaded) {
			Resource res = archive.getLoadStrategy().getExistingMofResource(aFile.getURI());
			if (res == null)
				return false;
			//must be manifest
			return !shouldSave(res);
		}

		if (getArchive().isModuleFile()) {
			ModuleFile m = (ModuleFile) getArchive();
			if (m.getExportStrategy() != null && m.getExportStrategy().hasSaved(aFile.getURI()))
				return false;
		}
		return shouldSave(aFile.getURI());
	}

	protected boolean shouldSave(Resource res) {
		if (!res.isModified() && getArchive().getOptions().saveOnlyDirtyMofResources())
			return false;

		return shouldSave(res.getURI().toString());
	}


	/**
	 * This is the one method through which all elements of an archive (file, nested archive, mof
	 * resource, or manifest) will be tested before saving. Subclasses can override to do something
	 * more specific
	 */
	protected boolean shouldSave(String uri) {
		return getFilter().shouldSave(uri, getArchive());
	}
}
