package net.ceos.project.poi.annotated.exception;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

import org.testng.annotations.DataProvider;
import org.testng.annotations.Test;

import net.ceos.project.poi.annotated.annotation.XlsElement;
import net.ceos.project.poi.annotated.annotation.XlsFreeElement;
import net.ceos.project.poi.annotated.bean.MultiTypeObject;
import net.ceos.project.poi.annotated.bean.SimpleObject;
import net.ceos.project.poi.annotated.bean.XlsConflictAnnotationIncompatibleHoriz;
import net.ceos.project.poi.annotated.bean.XlsConflictAnnotationIncompatibleVerti;
import net.ceos.project.poi.annotated.bean.XlsConflitFormulaHorizIncompatible;
import net.ceos.project.poi.annotated.bean.XlsConflitFormulaVertiIncompatible;
import net.ceos.project.poi.annotated.bean.XlsElementInvalidPosition;
import net.ceos.project.poi.annotated.bean.XlsElementOverwriteCell;
import net.ceos.project.poi.annotated.bean.XlsFreeElementInvalidObject;
import net.ceos.project.poi.annotated.bean.XlsFreeElementInvalidPositionCell;
import net.ceos.project.poi.annotated.bean.XlsFreeElementInvalidPositionRow;
import net.ceos.project.poi.annotated.bean.XlsFreeElementOverwriteCell;
import net.ceos.project.poi.annotated.core.Engine;
import net.ceos.project.poi.annotated.core.IEngine;
import net.ceos.project.poi.annotated.core.TestUtils;
import net.ceos.project.poi.annotated.core.XConfigCriteria;
import net.ceos.project.poi.annotated.definition.ExtensionFileType;

/**
 * Test the {@link ElementException}
 * 
 * @version 1.0
 * @author Carlos CRISTO ABREU
 */
public class ElementExceptionTest {

	@DataProvider
	public Object[][] collectionProvider() {
		/* collection null */
		List<Object> collectionNull = null;
		/* Collection empty */
		List<Object> collectionEmpty = new ArrayList<Object>();
		/* Collection with object null */
		List<Object> collection = new ArrayList<Object>();
		SimpleObject so = null;
		collection.add(so);
		
		return new Object[][] { 
			{ collectionNull, "CollectionNull", ExtensionFileType.XLS },
			{ collectionEmpty, "CollectionEmpty", ExtensionFileType.XLS },
			{ collection, "CollectionWithObjectEmpty", ExtensionFileType.XLSX }
		};
	}

	@DataProvider
	public Object[][] overwriteCellProvider(){
		return new Object[][] { 
			{ new XlsElementOverwriteCell() },
			{ new XlsFreeElementOverwriteCell() }
		};
	}

	@DataProvider
	public Object[][] invalidPositionProvider(){
		return new Object[][] { 
			{ new XlsElementInvalidPosition() },
			{ new XlsFreeElementInvalidPositionCell() },
			{ new XlsFreeElementInvalidPositionRow() }
		};
	}

	@DataProvider
	public Object[][] xlsConflictConfigurationProvider() {
		return new Object[][] { 
			{ new XlsConflitFormulaHorizIncompatible() },
			{ new XlsConflitFormulaVertiIncompatible() } };
	}

	@DataProvider
	public Object[][] xlsConflictAnnotationProvider() {
		return new Object[][] { 
			{ new XlsConflictAnnotationIncompatibleHoriz() },
			{ new XlsConflictAnnotationIncompatibleVerti() } };
	}

	/**
	 * Test an null object
	 * 
	 * @throws Exception
	 */
	@Test(expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "The entry object is null. Make sure you are sending a correct object.")
	public void testMarsharObjectNull() throws Exception {
		MultiTypeObject objNull = null;

		IEngine en = new Engine();
		en.marshalToByte(objNull);
	}

	/**
	 * Test an empty object
	 */
	@Test(expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "The entry object is null. Make sure you are sending a correct object.")
	public void testUnmarshalObjectNull() throws Exception {
		MultiTypeObject objEmpty = new MultiTypeObject();

		IEngine en = new Engine();
		byte[] generatedBytes = en.marshalToByte(objEmpty);

		MultiTypeObject charger = null;
		en.unmarshalFromByte(charger, generatedBytes);
	}

	/**
	 * Test an empty list & list with null object
	 * 
	 * @throws Exception
	 */
	@SuppressWarnings("rawtypes")
	@Test(dataProvider = "collectionProvider", expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "The entry object is null. Make sure you are sending a correct object.")
	public void testMarshalList(Collection collection, String fileName, ExtensionFileType extension) throws Exception {
		XConfigCriteria configCriteria = new XConfigCriteria();
		configCriteria.setFileName(fileName);
		configCriteria.overrideExtensionType(extension);
		
		IEngine en = new Engine();
		en.marshalAsCollectionAndSave(configCriteria, collection, TestUtils.WORKING_DIR_GENERATED_I);
	}


	/**
	 * Test a {@link XlsFreeElement} trying use a complex object
	 */
	@Test(expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "Complex objects are not allowed for this type! Review your configuration.")
	public void testMarshalXlsFreeElementInvalidObject() throws Exception {
		XlsFreeElementInvalidObject complexObject = new XlsFreeElementInvalidObject();

		IEngine en = new Engine();
		en.marshalToSheet(complexObject);
	}

	/**
	 * Test a {@link XlsElement} & {@link XlsFreeElement} trying write at one cell already used
	 */
	@Test(dataProvider = "overwriteCellProvider", expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "The element entry is trying to be set at one position already used. Review your configuration.")
	public void testMarshalXlsElementOverwriteCell(Object object) throws Exception {
		IEngine en = new Engine();
		en.marshalToWorkbook(object);
	}

	/**
	 * Test a {@link XlsElement} trying write at invalid position<br>
	 * Test a {@link XlsFreeElement} trying write at invalid cell position<br>
	 * Test a {@link XlsFreeElement} trying write at invalid row position<br>
	 */
//	@Test(dataProvider = "invalidPositionProvider", expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "The element entry has a invalid position, make sure you are setting a positive value and start at least by 1. Review your configuration.")
//	public void testMarshalXlsElementInvalidPosition(Object object) throws Exception {
//		IEngine en = new Engine();
//		en.marshalToFileOutputStream(object);
//	}

	/**
	 * Test a horizontal configuration exception conflict
	 */
	@Test(dataProvider = "xlsConflictConfigurationProvider", expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "Conflict at the configuration. Review your configuration.")
	public void testXlsConflictConfigurationException(Object incompatibleConfig) throws Exception {
		IEngine en = new Engine();
		en.marshalAndSave(incompatibleConfig, TestUtils.WORKING_DIR_GENERATED_I);
	}

	/**
	 * Test a non-conflict annotation type
	 */
	@Test(dataProvider = "xlsConflictAnnotationProvider", expectedExceptions = ElementException.class, expectedExceptionsMessageRegExp = "Conflict with annotation of type @XlsElement and @XlsFreeElement. Only one annotation type is valid per attribute.")
	public void testXlsConflictAnnotation(Object incompatibleConfig) throws Exception {
		IEngine en = new Engine();
		en.marshalAndSave(incompatibleConfig, TestUtils.WORKING_DIR_GENERATED_I);
	}
}

@@ -659,32 +659,33 @@
 d.bean.XlsConfli
+c
 tFormulaHorizInc
@@ -739,32 +739,33 @@
 d.bean.XlsConfli
+c
 tFormulaVertiInc
@@ -2723,32 +2723,33 @@
 %09%7B new XlsConfli
+c
 tFormulaHorizInc
@@ -2781,16 +2781,17 @@
 lsConfli
+c
 tFormula

fix error