/**
 * 
 */
package com.ejie.ad74a.process;

import java.util.Arrays;
import java.util.stream.Collectors;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import com.ejie.ad74a.exception.Ad74aException;
import com.ejie.ad74a.exception.BatchProcessException;
import com.ejie.ad74a.model.Pagos;
import com.ejie.ad74a.model.Procesos;
import com.ejie.ad74a.service.PagosService;
import com.ejie.ad74a.service.ProcesosService;
import com.ejie.ad74a.util.constantes.EstadosProcesosBatchEnum;
import com.ejie.ad74a.util.constantes.ProcesosBatchEnum;

/**
 * Proceso de relanzamiento de una factura que genera un nuevo informe Excel o
 * una nueva liquidacion para un id de factura dado en funcion de los parametros
 * que recibe
 * 
 * @author BICUGUAL
 *
 */
@Component(value = "pagoPrestador")
public class PagoPrestadorProcess implements IProcess {
	
	private static final Logger logger = LoggerFactory.getLogger(PagoPrestadorProcess.class);
	
	private static String ANADIR_PAGO = "A";
	private static String RECALCULAR_PAGO = "R";
	
	@Autowired
	PagosService pagosService;
	
	@Autowired
	ProcesosService procesosService;
	
	/**
	 * Metodo de ejecucion del proceso.
	 * 
	 * @param arg[0] : A- Añadir pago; R- recalcular pago
	 * @param arg[1] : Año para añadir o idPago para recalcular 
	 * @param arg[2] : Mes (no llega para recalcular)
	 * @param arg[2/3] : idProceso tabla AD74A98T00
	 * 
	 * Formato del parámetro:
	 * 	- A: @@A@@idProceso@@año@@mes@@
	 *  - R: @@R@@idProceso@@idPago@@
	 */
	@Override
	public void execute(String... args) throws BatchProcessException {
		
		Procesos proceso = new Procesos();
		try {
			
			String params = Arrays.asList(args).stream().map(i -> i).collect(Collectors.joining(", "));
			
			logger.debug("Params: {}", params);
			
			String operacion = args[0];
			
			
			String idProceso = null;//args.length == 3 &&  ? args[1] : null;
			
			if(ANADIR_PAGO.equalsIgnoreCase(operacion) && args.length > 3) {
				idProceso = args[3];
			}else if(RECALCULAR_PAGO.equalsIgnoreCase(operacion) && args.length > 2) {
				idProceso = args[2];
			}
				
			logger.debug("Operacion '{}' - idProceso '{}'", operacion, idProceso);
			
			// Buscar si existe el proceso en bbdd
			boolean addProceso = false;
			if(idProceso == null || "".equals(idProceso)) {
				addProceso = true;
			} else {
				proceso = new Procesos(Long.valueOf(idProceso));
				proceso = this.procesosService.find(proceso);
				addProceso = null == proceso? true: false;					
			}
			
			if(addProceso) {
				// Creamos un proceso nuevo
				// 1- Insertar el nuevo proceso en la tabla AD74A98T00
				proceso = new Procesos();
				proceso.setEstado98(EstadosProcesosBatchEnum.PENDIENTE.getId());
				proceso.setUsuAlta98("AD74A");
				if(ANADIR_PAGO.equalsIgnoreCase(operacion)) {					
					proceso.setTipoProceso98(ProcesosBatchEnum.ANADIR_PAGO_PRESTADOR.getId());
					proceso.setProceso98("añadir_pago_" + args[1] + "_" + args[2]);
				}else if(RECALCULAR_PAGO.equalsIgnoreCase(operacion)) {
					proceso.setTipoProceso98(ProcesosBatchEnum.RECALCULAR_PAGO_PRESTADOR.getId());
					proceso.setProceso98("recalcular_pago_" + args[1]);
				}
				proceso = this.procesosService.add(proceso);
			}
			
			if(ANADIR_PAGO.equalsIgnoreCase(operacion)) {
				this.procesosService.actualizarAIniciado(proceso);
				
				Long anyo = Long.valueOf(args[1]);
				String mes = args[2];
				
				logger.debug("Año '{}' - mes '{}'", anyo, mes);
				
				Pagos pago = new Pagos();
				pago.setAnyoPago74(anyo);
				pago.setMesPago74(mes);
				this.pagosService.anadirPago(pago);
				this.procesosService.actualizarAFinalizado(proceso);			
				
			}else if(RECALCULAR_PAGO.equalsIgnoreCase(operacion)) {
				this.procesosService.actualizarAIniciado(proceso);
				
				Long idPago = Long.valueOf(args[1]);
				
				logger.debug("idPago '{}'", idPago);
				
				Pagos pago = new Pagos(idPago);
				this.pagosService.recalcularPago(pago);
				this.procesosService.actualizarAFinalizado(proceso);			
				
			}else {
				logger.info("Tipo de cálculo no definido");
				proceso.setError98("Tipo de cálculo no definido");
				this.procesosService.actualizarAError(proceso);
			}
			
		} catch (Exception e) {
			String message = Ad74aException.escribirStackTrace(e);
			if(proceso.getIdProceso98() != null) {				
				proceso.setError98(message.substring(0, Math.min(message.length(), 799))); // Máximo 800
				this.procesosService.actualizarAError(proceso);
			}
			throw new BatchProcessException(e);
		}

	}

}
