/*
 * exe/util/t07bCFormatoFecha.java
 *
 * AGB, 11/09/2006
 * 
 *
 */

package com.ejie.aa20b.classes;

import java.text.DateFormat;
import java.text.ParsePosition;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;
import java.util.StringTokenizer;

//import error.t07bCError;
//import error.t07bEFechaErronea;

/**
 * Esta clase representa un conjunto de utilidades para el manejo de fechas
 */
public class Aa20bFormatoFecha {

	public static final int FECHA = 1;
	public static final int FECHA_HORA = 2;
	public static final int FECHA_HORA_SEGUNDOS = 3;
	public static final int HORA = 4;
	public static final int HORA_SEGUNDOS = 5;
	public static final int FECHA_YYYYMMDD = 6;
	public static final int FECHA_DDMMYYYY = 7;
	public static final int FECHAHORA_YYYYMMDD = 8;
	public static final int FECHAHORA_DDMMYYYY = 9;

	private static final String SEPARADOR_HORA = ":";

	/**
	 * Convierte una fecha (en milisegundos) en un dato de tipo String usando el
	 * formato usando la mascara por defecto y el locale especificado
	 * 
	 * @param alngFecha
	 *            Fecha a procesar (expresada en milisegundos).
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * 
	 * @return fecha formateada como un string.
	 */
	public String date2String(long alngFecha, Locale aLocale) {
		return date2String(new Date(alngFecha), aLocale, FECHA);
	}

	/**
	 * Convierte una fecha (en milisegundos) en un dato de tipo String usando el
	 * formato dado en la mascara y el locale especificado
	 * 
	 * @param alngFecha
	 *            Fecha a procesar expresada en milisegundos.
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * @param aintMascara
	 *            mascara a usar. Ver constantes para posibles opciones
	 * 
	 * @return fecha formateada como un string.
	 */
	public String date2String(long alngFecha, Locale aLocale, int aintMascara) {
		return date2String(new Date(alngFecha), aLocale, aintMascara);
	}

	/**
	 * Convierte una fecha (java.util.Date) en un dato de tipo String usando el
	 * formato usando la mascara por defecto y el locale especificado
	 * 
	 * @param adatFecha
	 *            Fecha a procesar.
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * 
	 * @return fecha formateada como un string.
	 */
	public static String date2String(Date adatFecha, Locale aLocale) {
		return date2String(adatFecha, aLocale, FECHA);
	}

	/**
	 * Convierte una fecha (java.util.Date) en un dato de tipo String usando el
	 * formato dado en la mascara y el locale especificado
	 * 
	 * @param adatFecha
	 *            Fecha a procesar.
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * @param aintMascara
	 *            mascara a usar. Ver constantes para posibles opciones
	 * 
	 * @return fecha formateada como un string.
	 */
	public static String date2String(Date adatFecha, Locale aLocale,
			int aintMascara) {
		if (adatFecha == null)
			return "";
		DateFormat dateFormatter;
		switch (aintMascara) {
		case FECHA:
			dateFormatter = DateFormat.getDateInstance(DateFormat.SHORT,
					aLocale);
			break;
		case FECHA_HORA:
			dateFormatter = DateFormat.getDateTimeInstance(DateFormat.SHORT,
					DateFormat.SHORT, aLocale);
			break;
		case FECHA_HORA_SEGUNDOS:
			dateFormatter = DateFormat.getDateTimeInstance(DateFormat.SHORT,
					DateFormat.MEDIUM, aLocale);
			break;
		case HORA:
			dateFormatter = DateFormat.getTimeInstance(DateFormat.SHORT,
					aLocale);
			break;
		case HORA_SEGUNDOS:
			dateFormatter = DateFormat.getTimeInstance(DateFormat.MEDIUM,
					aLocale);
			break;
		case FECHA_YYYYMMDD:
			dateFormatter = new SimpleDateFormat("yyyy/MM/dd");
			break;
		case FECHA_DDMMYYYY:
			dateFormatter = new SimpleDateFormat("dd/MM/yyyy");
			break;
		case FECHAHORA_YYYYMMDD:
			dateFormatter = new SimpleDateFormat("yyyy/MM/dd HH:mm");
			break;
		case FECHAHORA_DDMMYYYY:
			dateFormatter = new SimpleDateFormat("dd/MM/yyyy HH:mm");
			break;
		default:
			dateFormatter = DateFormat.getDateInstance(DateFormat.SHORT,
					aLocale);
			break;
		}
		return dateFormatter.format(adatFecha);
	}

	/**
	 * Convierte una fecha (que viene como String) en un dato de tipo Date
	 * (java.util.Date) deduciendo el formato especificado.
	 * 
	 * @param astrFecha
	 *            Fecha a procesar.
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * 
	 * @return fecha formateada como un java.util.Date
	 * @throws r76bEFechaErronea
	 *             si la fecha no es correcta.
	 */
	public static Date string2Date(String astrFecha, Locale aLocale)
			throws Exception {
		// int lintMascara = 0;

		String lstrSeparadorHora = getSeparadorHora(aLocale);

		StringTokenizer st = new StringTokenizer(astrFecha);
		switch (st.countTokens()) {
		case (1): // viene solo una fecha o una hora
			if (astrFecha.indexOf(lstrSeparadorHora) != -1) {
				StringTokenizer st2 = new StringTokenizer(st.nextToken(),
						lstrSeparadorHora);
				switch (st2.countTokens()) {
				case (1): // hora:minutos
					return string2Date(astrFecha, aLocale, HORA);
				case (2): // hora:minutos:segundos
					return string2Date(astrFecha, aLocale, HORA_SEGUNDOS);
				default:
					String[] lParametrosMensaje = { astrFecha, "" };
					// t07bCError lError = new t07bCError(1101, "CFormatoFecha",
					// "string2Date", lParametrosMensaje);
					throw new Exception();
				}
			} else {
				// viene una fecha
				return string2Date(astrFecha, aLocale, FECHA);
			}
		case (2): // viene fecha y hora
			if (aLocale.getLanguage().contains("eu"))
				return string2Date(astrFecha, aLocale, FECHAHORA_YYYYMMDD);
			else
				return string2Date(astrFecha, aLocale, FECHAHORA_DDMMYYYY);

		case (3): // viehe fecha y hora y AM/PM
			String laux = st.nextToken();
			StringTokenizer st3 = new StringTokenizer(laux, lstrSeparadorHora);
			switch (st3.countTokens()) {
			case (2): // hora:minutos
				return string2Date(astrFecha, aLocale, FECHA_HORA);
			case (3): // hora:minutos:segundos
				return string2Date(astrFecha, aLocale, FECHA_HORA_SEGUNDOS);
			default:
				String[] lParametrosMensaje = { astrFecha, "" };
				// t07bCError lError = new t07bCError(1101, "CFormatoFecha",
				// "string2Date", lParametrosMensaje);
				throw new Exception();
			}
		default:
			String[] lParametrosMensaje = { astrFecha, "" };
			// t07bCError lError = new t07bCError(1101, "CFormatoFecha",
			// "string2Date", lParametrosMensaje);
			throw new Exception();
		}

	}

	/**
	 * Convierte una fecha (que viene como String) en un dato de tipo Date
	 * (java.util.Date) usando el formato dado en la mascara y el locale
	 * especificado
	 * 
	 * @param astrFecha
	 *            Fecha a procesar.
	 * @param aLocale
	 *            locale a usar para formatear la fecha
	 * @param aintMascara
	 *            mascara a usar. Ver constantes para posibles opciones
	 * 
	 * @return fecha formateada como un java.util.Date
	 * @throws r76bEFechaErronea
	 *             si la fecha no es correcta.
	 */
	public static Date string2Date(String astrFecha, Locale aLocale,
			int aintMascara) throws Exception {
		DateFormat dateFormatter;
		switch (aintMascara) {
		case FECHA:
			dateFormatter = SimpleDateFormat.getDateInstance(DateFormat.SHORT,
					aLocale);
			break;
		case FECHA_HORA:
			dateFormatter = SimpleDateFormat.getDateTimeInstance(
					DateFormat.SHORT, DateFormat.SHORT, aLocale);
			break;
		case FECHA_HORA_SEGUNDOS:
			dateFormatter = SimpleDateFormat.getDateTimeInstance(
					DateFormat.SHORT, DateFormat.MEDIUM, aLocale);
			break;
		case HORA:
			dateFormatter = SimpleDateFormat.getTimeInstance(DateFormat.SHORT,
					aLocale);
			break;
		case HORA_SEGUNDOS:
			dateFormatter = SimpleDateFormat.getTimeInstance(DateFormat.MEDIUM,
					aLocale);
			break;
		case FECHAHORA_YYYYMMDD:
			SimpleDateFormat sdf;
			sdf = new SimpleDateFormat("yyyy/MM/dd HH:mm");

			return sdf.parse(astrFecha);

		case FECHAHORA_DDMMYYYY:
			SimpleDateFormat sdf2;
			sdf2 = new SimpleDateFormat("dd/MM/yyyy HH:mm");
			return sdf2.parse(astrFecha);
		default:
			dateFormatter = SimpleDateFormat.getDateInstance(DateFormat.SHORT,
					aLocale);
			break;
		}
		try {
			dateFormatter.setLenient(false);
			Date ldatFecha = dateFormatter.parse(astrFecha,
					new ParsePosition(0));
			if (ldatFecha == null) {
				String[] lParametrosMensaje = { astrFecha, "ldatFecha=null" };
				/*
				 * t07bCError lError = new t07bCError(1101, "CFormatoFecha",
				 * "string2Date", lParametrosMensaje);
				 */
				throw new Exception();
			}
			return ldatFecha;
		} catch (Exception e) {
			// String[] lParametrosMensaje = { astrFecha, e.getMessage() };
			/*
			 * t07bCError lError = new t07bCError(1101, "CFormatoFecha",
			 * "string2Date", lParametrosMensaje);
			 */
			throw new Exception(e);
		}
	}

	private static String getSeparadorHora(Locale aLocale) {
		return SEPARADOR_HORA;
	}

	/**
	 * Convierte una fecha (java.util.Date) en un dato de tipo timestamp
	 * (java.sql.Timestamp). Esto permite manejar las fechas de Oracle (DATE =
	 * fecha y hora) mientras las clases utilizan java.util.Date. Si el
	 * par�metro es null, devuelve null.
	 * 
	 * @param adatFecha
	 *            Fecha a procesar.
	 * 
	 * @return Timestamp.
	 */
	public static java.sql.Timestamp date2Timestamp(java.util.Date adatFecha) {
		if (adatFecha == null) {
			return null;
		} else {
			return new java.sql.Timestamp(adatFecha.getTime());
		}
	}

	/**
	 * Convierte una fecha en milisegundos (long) en un dato de tipo timestamp
	 * (java.sql.Timestamp). Esto permite manejar las fechas de Oracle (DATE =
	 * fecha y hora) mientras las clases utilizan fechas en milisegundos (por
	 * ejemplo SystemCurrentTimeMillis()).
	 * 
	 * @param alngFecha
	 *            milisegundos de una fecha.
	 * @return Timestamp.
	 */
	public java.sql.Timestamp date2Timestamp(long alngFecha) {
		return date2Timestamp(new java.util.Date(alngFecha));
	}

	/**
	 * @@@ DGS: 13/02/2001 ESTE METODO HAY QUE DEJAR DE USARLO Convierte un
	 *     java.lang.String del tipo (YYYYMMDD) en un dato de tipo Date
	 *     (java.util.Date).
	 * @param astrFecha
	 *            String a procesar.
	 * @throws r76bEParseoException
	 *             si se produce un error en la transformacion de tipos.
	 * @return Timestamp.
	 * @deprecated este metodo no deberia usarse mas
	 */
	// public static java.util.Date StringToDate(String astrFecha) throws
	// r76bEParseoException {
	//
	// Date cdatFecha = null;
	//
	// try{
	//
	// int cintAno = new Integer(astrFecha.substring(0,4).trim()).intValue();
	// int cintMes = new Integer(astrFecha.substring(4,6).trim()).intValue();
	// int cintDia = new Integer(astrFecha.substring(6,8).trim()).intValue();
	//
	// cdatFecha = new Date(cintAno-1900, cintMes, cintDia);
	//
	// } catch(Exception e) {
	// String[] lParametrosMensaje = {"String", "Integer", e.getMessage()};
	// r76bCError lError = new r76bCError(3000, "es.aliatec.util.CFormatoFecha",
	// "StringToDate");
	// throw new r76bEParseoException(lError);
	// }
	// return(cdatFecha);
	// }

}
