import junit.framework.TestCase;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;

import javax.xml.transform.Result;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.TransformerFactoryConfigurationError;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

import org.junit.*;
import org.junit.Test;

public class JI9029628 extends TestCase{
	public static final String TEST_DATA_FOLDER = "testdata/xml/xslt/aim/transfer_invoice_0_32/"; 

	/** 
	 * Test of the invoice XSLT. Unfortunately fails with the JDK's internal 
	 * Xalan, but should not fail (place xalan.jar (+dependencies) or saxon in 
	 * the classpath to see a success). 
	 */ 
	@Test 
	public void testXSLFailingInJDKWithException() throws Exception { 
		File resultFile = doTransformation("transferInvoice_0_32.xsl", "38_invoices_0_32.xml"); 
		assertSameContent("reference.txt", resultFile); 
	} 

	private Transformer getTransformer(Source xslSource) throws TransformerFactoryConfigurationError, TransformerConfigurationException { 
		TransformerFactory tFactory = TransformerFactory.newInstance(); 
		return tFactory.newTransformer(xslSource); 
	} 

	/** 
	 * Method transforming the data file and return the output file. 
	 */ 
	protected File doTransformation(String styleSheet, String dataFile) throws Exception { 
		Source xslSource = new StreamSource(new File(TEST_DATA_FOLDER, styleSheet)); 
		Source dataSource = new StreamSource(new File(TEST_DATA_FOLDER, dataFile)); 

		File resultFile = new File(TEST_DATA_FOLDER, "output.txt"); 

		Transformer transformer = getTransformer(xslSource); 

		Result res = null; 
		FileOutputStream out = null; 
		try { 
			out = new FileOutputStream(resultFile, false); 
			res = new StreamResult(out); 

			transformer.transform(dataSource, res); 
		} finally { 
			if (out != null) { 
				out.close(); 
			} 
		} 

		return resultFile; 
	} 

	/** 
	 * Reads the contents of the given file into a string. 
	 * WARNING: this method adds a final line feed even if the last line of the file doesn't contain one. 
	 * 
	 * @param f 
	 * The file to read 
	 * @param progressListener 
	 * An optional progress listener, use {@code null} if not needed 
	 * @return The content of the file as a string, with line terminators as \"n" 
	 * for all platforms 
	 * @throws IOException 
	 * If there was an error reading 
	 */ 
	public String getFileContentAsString(File f) throws IOException { 
		if (f == null) { 
			throw new IllegalArgumentException("file cannot be null"); 
		} 

		BufferedReader reader = null; 
		try { 
			reader = new BufferedReader(new FileReader(f)); 
			String line; 
			StringBuilder sb = new StringBuilder(); 
			while ((line = reader.readLine()) != null) { 
				sb.append(line).append("\n"); 
			} 
			return sb.toString(); 
		} 
		finally { 
			if (reader != null) { 
				reader.close(); 
			} 
		} 
	} 

	public void assertSameContent(String referenceFile, File resultFile) throws Exception { 
		String toVerify = getFileContentAsString(resultFile); 
		String reference = getFileContentAsString(new File(TEST_DATA_FOLDER, referenceFile)); 
		assertEquals(reference, toVerify); 
	} 
}
