//------------------------------------------------------------------------------
// Copyright (c) 2005, 2006 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.common.xml;

import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileWriter;
import java.io.InputStream;
import java.io.Writer;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;

import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

import org.eclipse.epf.common.CommonPlugin;

/**
 * A wrapper over the XSLT processor bundled with the JRE.
 * 
 * @author Kelvin Low
 * @since 1.0
 */
public class XSLTProcessor {

	// If true, cache the compiled the XSL transformer with the compiled XSL
	// templates.
	private static boolean cacheXSL;

	// Caches the XSL transformers.
	private static Map transformerCache;

	static {
		String cacheXSLProperty = CommonPlugin.getDefault().getString(
				"cacheXSL"); //$NON-NLS-1$
		if (cacheXSLProperty != null && !cacheXSLProperty.startsWith("[")) { //$NON-NLS-1$
			cacheXSL = Boolean.getBoolean(cacheXSLProperty);
		} else {
			cacheXSL = true;
		}
		if (cacheXSL) {
			transformerCache = new HashMap();
		}
		
		// set the expansion line limit
		System.setProperty("entityExpansionLimit", "1000000");

	}

	/**
	 * Default private constructor to prevent this class from being
	 * instantiated.
	 */
	private XSLTProcessor() {
	}

	/**
	 * Executes the XSL transformation given the XSL source, XML source, target
	 * output and encoding.
	 * 
	 * @param xslSource
	 *            The XSL source.
	 * @param xmlSource
	 *            The XML source.
	 * @param output
	 *            The output target.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(Source xslSource, Source xmlSource,
			Writer output, Properties params, String encoding) throws Exception {
		if (xslSource != null && xmlSource != null) {
			Transformer transformer = null;
			String xslFile = xslSource.getSystemId();
			if (cacheXSL && xslFile != null) {
				synchronized (transformerCache) {
					transformer = (Transformer) transformerCache.get(xslFile);
					if (transformer == null) {
						TransformerFactory factory = TransformerFactory
								.newInstance();
						transformer = factory.newTransformer(xslSource);
						transformerCache.put(xslFile, transformer);
					}
				}
			} else {
				TransformerFactory factory = TransformerFactory.newInstance();
				transformer = factory.newTransformer(xslSource);
			}
			if (params != null && params.size() > 0) {
				for (Iterator i = params.keySet().iterator(); i.hasNext();) {
					String paramName = (String) i.next();
					String paramValue = params.getProperty(paramName);
					transformer.setParameter(paramName, paramValue);
				}
			}
			if (encoding != null && encoding.length() > 0) {
				transformer.setOutputProperty("encoding", encoding); //$NON-NLS-1$
			} else {
				transformer.setOutputProperty("encoding", "utf-8"); //$NON-NLS-1$ //$NON-NLS-2$
			}
			transformer.transform(xmlSource, new StreamResult(output));
		}
	}

	/**
	 * Executes the XSL transformation given the XSL source, XML source, target
	 * output and encoding.
	 * 
	 * @param xslSource
	 *            The XSL source.
	 * @param xmlSource
	 *            The XML source.
	 * @param output
	 *            The output target.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(Source xslSource, Source xmlSource,
			Writer output, String encoding) throws Exception {
		transform(xslSource, xmlSource, output, null, encoding);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML source,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML source.
	 * @param output
	 *            The output target.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, Source xmlSource,
			Writer output, Properties params, String encoding) throws Exception {
		InputStream xslInput = getXslInputStream(xslUri);
		if (xslInput != null) {
			StreamSource xslSource = new StreamSource(xslInput);
			xslSource.setSystemId(new File(xslUri));
			transform(xslSource, xmlSource, output, params, encoding);
			try {
				xslInput.close();
			} catch (Exception e) {
			}
		}
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML source,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML source.
	 * @param output
	 *            The output target.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, Source xmlSource,
			Writer output, String encoding) throws Exception {
		transform(xslUri, xmlSource, output, null, encoding);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param output
	 *            The output target.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, String xmlStr, Writer output,
			Properties params, String encoding) throws Exception {
		InputStream xslInput = getXslInputStream(xslUri);
		if (xslInput != null) {
			StreamSource xslSource = new StreamSource(xslInput);
			xslSource.setSystemId(new File(xslUri));

			byte[] xml = xmlStr.getBytes("utf-8"); //$NON-NLS-1$
			ByteArrayInputStream xmlInput = new ByteArrayInputStream(xml);
			StreamSource xmlSource = new StreamSource(xmlInput);

			transform(xslSource, xmlSource, output, params, encoding);

			try {
				xslInput.close();
			} catch (Exception e) {
			}
		}
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param output
	 *            The output target.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, String xmlStr, Writer output,
			String encoding) throws Exception {
		transform(xslUri, xmlStr, output, null, encoding);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param file
	 *            The output file.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, String xmlStr, File file,
			Properties params, String encoding) throws Exception {
		FileWriter output = new FileWriter(file);
		if (output != null) {
			transform(xslUri, xmlStr, output, params, encoding);
			try {
				output.close();
			} catch (Exception e) {
			}
		}
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string,
	 * target output and encoding.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param file
	 *            The output file.
	 * @param encoding
	 *            The target encoding.
	 */
	public static void transform(String xslUri, String xmlStr, File file,
			String encoding) throws Exception {
		transform(xslUri, xmlStr, file, null, encoding);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML source
	 * and target output.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML source.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, Source xmlSource,
			Properties params, Writer output) throws Exception {
		transform(xslUri, xmlSource, output, params, null);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML source
	 * and target output.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML source.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, Source xmlSource, Writer output)
			throws Exception {
		transform(xslUri, xmlSource, output, null, null);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string
	 * and target output.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, String xmlStr,
			Properties params, Writer output) throws Exception {
		transform(xslUri, xmlStr, output, params, null);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string
	 * and target output.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, String xmlStr, Writer output)
			throws Exception {
		transform(xslUri, xmlStr, output, null, null);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string
	 * and target output file.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param params
	 *            The parameters for the XSL transformation.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, String xmlStr,
			Properties params, File file) throws Exception {
		transform(xslUri, xmlStr, file, params, null);
	}

	/**
	 * Executes the XSL transformation given the XSL stylesheet URI, XML string
	 * and target output file.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 * @param xmlStr
	 *            The XML string.
	 * @param output
	 *            The output target.
	 */
	public static void transform(String xslUri, String xmlStr, File file)
			throws Exception {
		transform(xslUri, xmlStr, file, null, null);
	}

	/**
	 * Returns the XSL input stream given the XSL stylesheet URI.
	 * 
	 * @param xslURI
	 *            The XSL stylesheet URI.
	 */
	private static InputStream getXslInputStream(String xslUri) {
		InputStream xslInput = null;
		try {
			xslInput = new FileInputStream(xslUri);
		} catch (Exception e) {
			if (xslInput == null) {
				xslInput = XSLTProcessor.class.getClassLoader()
						.getResourceAsStream(xslUri);
			}
		}
		return xslInput;
	}

}
