//------------------------------------------------------------------------------
// Copyright (c) 2005, 2007 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 implementation
//------------------------------------------------------------------------------
package org.eclipse.epf.publishing.services;

import java.io.File;
import java.util.Collection;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.epf.common.serviceability.DebugTrace;
import org.eclipse.epf.library.configuration.ConfigurationHelper;
import org.eclipse.epf.library.util.FileNameGenerator;
import org.eclipse.epf.library.util.LibraryUtil;
import org.eclipse.epf.publishing.PublishingPlugin;
import org.eclipse.epf.publishing.PublishingResources;
import org.eclipse.epf.uma.MethodConfiguration;
import org.eclipse.epf.uma.MethodLibrary;

/**
 * The abstract base class for all Publish Managers.
 * <p>
 * Use the org.eclipse.epf.publishing.ui.publishers extension point to extend
 * this class if you need to customize the publishing.
 * 
 * @author Jinhua Xi
 * @since 1.0
 */
public abstract class AbstractPublishManager {

	protected static boolean debug = PublishingPlugin.getDefault()
			.isDebugging();

	protected static boolean profiling = PublishingPlugin.getDefault()
			.isProfiling();

	protected String pubDir;

	protected MethodConfiguration config;

	protected PublishHTMLOptions options;

	protected AbstractViewBuilder viewBuilder;

	protected boolean success = false;

	/**
	 * Creates a new instance.
	 */
	public AbstractPublishManager() {
	}

	/**
	 * Initilizes the publishing manager.
	 * 
	 * @param pubDir
	 *            the publish directory
	 * @param config
	 *            a method configuration
	 * @param options
	 *            the publishing options
	 */
	public void init(String pubDir, MethodConfiguration config,
			PublishOptions options) {
		this.pubDir = pubDir;

		if (!this.pubDir.endsWith(File.separator)) {
			this.pubDir += File.separator;
		}

		this.config = config;
		if (options instanceof PublishHTMLOptions) {
			this.options = (PublishHTMLOptions) options;
		} else {
			throw new IllegalArgumentException();
		}
		this.viewBuilder = createViewBuilder();

		// clear the file name cache
		// NameCache.getInstance().clear();
	}

	/**
	 * get the publishing view builder. The view builder is responsible to build
	 * the publishing views and contents.
	 * 
	 * @return AbstractViewBuilder
	 */
	public AbstractViewBuilder getViewBuilder() {
		return this.viewBuilder;
	}

	public ISiteGenerator getSiteGenerator() {
		return viewBuilder.getSiteGenerator();
	}

	/**
	 * do publishing. The publishing process is defined in three steps.
	 * prePublish to do some preparation before the actual publishing doPublish
	 * to publish the views and contents postPublish to do some cleanup work
	 * after publish. Extended classes can override these methods to achieve
	 * additional publishing results.
	 * 
	 * @param monitor
	 *            IProgressMonitor
	 * @throws PublishingServiceException
	 */
	public void publish(IProgressMonitor monitor)
			throws PublishingServiceException {

		if (options != null) {
			options.validate();
		}

		// clear the file name cache so that the file name will be based on the latest library data
		// this can avoid the cases where element name changed before publishing
		FileNameGenerator.INSTANCE.clear();
		
		long beginTime = 0L;
		long startTime = 0L;

		// do a gc before getting stared
		Runtime.getRuntime().gc();
		
		try {
			ConfigurationHelper.getDelegate().setPublishingMode(true);
			
			if (profiling) {
				beginTime = startTime = System.currentTimeMillis();
			}
			
			prePublish(monitor);
			if (profiling) {
				DebugTrace.print(this, "prePublish", //$NON-NLS-1$
						(System.currentTimeMillis() - startTime) + " ms"); //$NON-NLS-1$
			}

			if (profiling) {
				startTime = System.currentTimeMillis();
			}
						
			doPublish(monitor);
			if (profiling) {
				DebugTrace.print(this, "doPublish", //$NON-NLS-1$
						(System.currentTimeMillis() - startTime) + " ms"); //$NON-NLS-1$
			}

			if (profiling) {
				startTime = System.currentTimeMillis();
			}
			postPublish(monitor);
			if (profiling) {
				DebugTrace.print(this, "postPublish", //$NON-NLS-1$
						(System.currentTimeMillis() - startTime) + " ms"); //$NON-NLS-1$
			}

			success = true;
		} catch (Exception e) {
			throw new PublishingServiceException(e);
		} finally {
			ConfigurationHelper.getDelegate().setPublishingMode(false);
			if (profiling) {
				System.out
						.println("Time taken to publish configuration '" + config.getName() //$NON-NLS-1$
								+ "': " + (System.currentTimeMillis() - beginTime) + " ms"); //$NON-NLS-1$ //$NON-NLS-2$
			}
		}
	}

	protected Collection<Resource> loadLibrary(IProgressMonitor monitor) {
		// first of all, we need to load the library,
		// otherwise, some relationships and opposite features are not
		// established
		long startTime = 0L;
		monitor.subTask(PublishingResources.loadLibraryTask_name);
		if (profiling) {
			startTime = System.currentTimeMillis();
		}
		
		Collection<Resource> changedResources = LibraryUtil.loadAll((MethodLibrary) config.eContainer());
		if (profiling) {
			DebugTrace.print(this, "loadLibrary", "LibraryUtil.loadAll: " //$NON-NLS-1$  //$NON-NLS-2$
							+ (System.currentTimeMillis() - startTime)
							+ " ms"); //$NON-NLS-1$
		}

		return changedResources;
	}
	
//	protected void unloadResources(Collection<Resource> resources) {
//		
//		//Runtime.getRuntime().gc();
//		//long m1 = Runtime.getRuntime().freeMemory()/1000000;
//		PersistenceUtil.unload(resources);
//		//Runtime.getRuntime().gc();		
//		//long m2 = Runtime.getRuntime().freeMemory()/1000000;
//		//System.out.println("*** " + Long.toString(m2-m1) + " MB freed by unloading resources");
//	}
//
//	protected void disposeDiagramManagers(Collection<DiagramManager> mgrs, Collection<DiagramManager> keeplist) {
//		for ( Iterator<DiagramManager> it = mgrs.iterator(); it.hasNext(); ) {
//			DiagramManager mgr = it.next();
//			if ( keeplist == null || !keeplist.contains(mgr) ) {
//				mgr.dispose();
//			}
//		}
//	}
	
	/**
	 * Disposes the object. Once disposed, the object is not valid any more.
	 */
	public void dispose() {
		if (viewBuilder != null) {
			viewBuilder.dispose();
			viewBuilder = null;
		}
	}

	/**
	 * abstract method to get the url to the published site
	 * 
	 * @return String the url
	 */
	public abstract String getPublishedUrl();

	/**
	 * abstract method to get the url to the publish report
	 * 
	 * @return String
	 */
	public abstract String getPublishReportUrl();

	protected abstract AbstractViewBuilder createViewBuilder();

	protected abstract void prePublish(IProgressMonitor monitor)
			throws Exception;

	protected abstract void doPublish(IProgressMonitor monitor)
			throws Exception;

	protected abstract void postPublish(IProgressMonitor monitor)
			throws Exception;

}
