package com.rjconsultores.ventaboletos.service.impl;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.rjconsultores.ventaboletos.dao.CorridaTramoDAO;
import com.rjconsultores.ventaboletos.dao.GP_PricingDAO;
import com.rjconsultores.ventaboletos.dao.TramoDAO;
import com.rjconsultores.ventaboletos.entidad.GP_PricingClase;
import com.rjconsultores.ventaboletos.entidad.GP_PricingCorrida;
import com.rjconsultores.ventaboletos.entidad.GP_PricingMarca;
import com.rjconsultores.ventaboletos.entidad.GP_PricingMercado;
import com.rjconsultores.ventaboletos.entidad.GP_PricingOcupaAntecipa;
import com.rjconsultores.ventaboletos.entidad.GP_PricingRuta;
import com.rjconsultores.ventaboletos.entidad.GP_PricingVigencia;
import com.rjconsultores.ventaboletos.entidad.Tramo;
import com.rjconsultores.ventaboletos.service.GP_PricingRevisaoValoresService;
import com.rjconsultores.ventaboletos.utilerias.MoneyHelper;
import com.rjconsultores.ventaboletos.vo.pricing.GP_PricingRevisaoValoresVO;

@Service("gp_pricingRevisaoValoresService")
public class GP_PricingRevisaoValoresServiceImpl implements GP_PricingRevisaoValoresService {

	private static final Logger log = LogManager.getLogger(GP_PricingRevisaoValoresServiceImpl.class);

	@Autowired
	private GP_PricingDAO pricingDAO;
	@Autowired
	private TramoDAO tramoDao;
	@Autowired
	private CorridaTramoDAO corridaTramoDAO;
	
	private static final BigDecimal HUNDRED = new BigDecimal(100);
	

	@Override
	public List<GP_PricingRevisaoValoresVO> obtenerTodos() {
		return null;
	}

	@Override
	public GP_PricingRevisaoValoresVO obtenerID(Long id) {
		return null;
	}

	@Override
	public GP_PricingRevisaoValoresVO suscribir(GP_PricingRevisaoValoresVO entidad) {
		return null;
	}

	@Override
	public GP_PricingRevisaoValoresVO actualizacion(GP_PricingRevisaoValoresVO entidad) {
		return null;
	}

	@Override
	public void borrar(GP_PricingRevisaoValoresVO entidad) {
	}

	public List<GP_PricingRevisaoValoresVO> buscarPricingRevisaoValoresVO(List<GP_PricingVigencia> lsPricingVigencia,
			List<GP_PricingClase> lsPricingClase,
			List<GP_PricingMarca> lsPricingMarca, List<GP_PricingMercado> lsPricingMercado,
			List<GP_PricingOcupaAntecipa> lsPricingOcupaAntecipa, List<GP_PricingCorrida> lsPricingCorrida,
			List<GP_PricingRuta> lsPricingRuta) {
		List<Integer> classeServicioIds = validaPricingClasseServico(lsPricingClase);
		List<Integer> marcaIds = validaPricingMarca(lsPricingMarca);
		List<Integer> rutaIds = validaPricingRuta(lsPricingRuta);
		List<Integer> tramoIds = validaPricingTramo(lsPricingMercado);
		tramoIds = validaPricingCorrida(lsPricingCorrida, tramoIds);
		
		
		List<GP_PricingRevisaoValoresVO> pricingRevisaoValoresVOs = pricingDAO.buscarPricingRevisaoValoresVO(classeServicioIds, marcaIds, rutaIds, tramoIds ,lsPricingVigencia);
		return validaDescontosCadastradosPricing(pricingRevisaoValoresVOs, lsPricingOcupaAntecipa);
	}

	private List<GP_PricingRevisaoValoresVO> validaDescontosCadastradosPricing(List<GP_PricingRevisaoValoresVO> pricingRevisaoValoresVOs, List<GP_PricingOcupaAntecipa> lsPricingOcupaAntecipa) {
		List<GP_PricingRevisaoValoresVO> retornoPricingRevisaoValoresVOs = new ArrayList<GP_PricingRevisaoValoresVO>();
		if(!lsPricingOcupaAntecipa.isEmpty()) {
			for (GP_PricingOcupaAntecipa gp_PricingOcupaAntecipa : lsPricingOcupaAntecipa) {
				for (GP_PricingRevisaoValoresVO gp_PricingRevisaoValoresVO : pricingRevisaoValoresVOs) {
					GP_PricingRevisaoValoresVO revisaoValoresVO = new GP_PricingRevisaoValoresVO(gp_PricingRevisaoValoresVO);
					BigDecimal tarifaPricing = BigDecimal.ZERO;
					String desconto = null;
					String antecipacao = null;
					String ocupacao = null;
					if(gp_PricingOcupaAntecipa.getPorcentaje()!= null) {
						tarifaPricing = MoneyHelper.getValorDescontadoPercentual(gp_PricingRevisaoValoresVO.getTarifaAtual(), gp_PricingOcupaAntecipa.getPorcentaje());
						desconto = gp_PricingOcupaAntecipa.getPorcentaje()+"%";
					}else {
						tarifaPricing = gp_PricingRevisaoValoresVO.getTarifaAtual().subtract( gp_PricingOcupaAntecipa.getImporte());
						desconto = MoneyHelper.getValor(gp_PricingOcupaAntecipa.getImporte());
					}
					antecipacao = gp_PricingOcupaAntecipa.getCantdiasmin() +" - "+ gp_PricingOcupaAntecipa.getCantdiasmax();
					ocupacao = gp_PricingOcupaAntecipa.getOcupacioninicial() +" - "+ gp_PricingOcupaAntecipa.getOcupacionfinal();
					revisaoValoresVO.setTarifaComPricing(tarifaPricing);
					revisaoValoresVO.setDesconto(desconto);
					revisaoValoresVO.setAntecipacao(antecipacao);
					revisaoValoresVO.setOcupacao(ocupacao);
					retornoPricingRevisaoValoresVOs.add(revisaoValoresVO);
				}
			}
			
		}
		
		return retornoPricingRevisaoValoresVOs;
	}

	private List<Integer> validaPricingCorrida(List<GP_PricingCorrida> lsPricingCorrida, List<Integer> tramoIds) {
		Set<Integer> tramosCorrida = new HashSet<Integer>(tramoIds);
		for (GP_PricingCorrida gp_PricingCorrida : lsPricingCorrida) {
			List<Tramo> listTramo =  corridaTramoDAO.buscarTramoPorCorridaId(gp_PricingCorrida.getCorridaCtrl().getCorridaId());
			for (Tramo tramo : listTramo) {
				tramosCorrida.add(tramo.getTramoId());
			}
		}
		return new ArrayList<Integer>(tramosCorrida);
	}

	private List<Integer> validaPricingTramo(List<GP_PricingMercado> lsPricingMercado) {
		List<Tramo> tramos = new ArrayList<Tramo>();
		for (GP_PricingMercado gp_PricingMercado : lsPricingMercado) {
			tramos =  tramoDao.obtenerTramosPorOrigemDestino(gp_PricingMercado.getOrigen(), gp_PricingMercado.getDestino());
		}
		Set<Integer> tramosIds = new HashSet<Integer>();
		if(tramos!= null && !tramos.isEmpty()) {
			for (Tramo tramo : tramos) {
				tramosIds.add(tramo.getTramoId());				
			}
		}
		
		
		return new ArrayList<Integer>(tramosIds);
	}

	private List<Integer> validaPricingRuta(List<GP_PricingRuta> lsPricingRuta) {
		List<Integer> rutaIds = null;
		if (!lsPricingRuta.isEmpty()) {
			rutaIds = new ArrayList<Integer>();
			for (GP_PricingRuta ruta : lsPricingRuta) {
				if (ruta.getRuta().getRutaId() != -1) {
					rutaIds.add(ruta.getRuta().getRutaId());
				}
			}
		}
		return rutaIds;
	}

	private List<Integer> validaPricingMarca(List<GP_PricingMarca> lsPricingMarca) {
		List<Integer> marcaIds = null;
		if (!lsPricingMarca.isEmpty()) {
			marcaIds = new ArrayList<Integer>();
			for (GP_PricingMarca marca : lsPricingMarca) {
				if (marca.getMarca().getMarcaId() != -1) {
					marcaIds.add(marca.getMarca().getMarcaId().intValue());
				}
			}
		}
		return marcaIds;
	}

	/**
	 * @param lsPricingClase
	 * @return
	 */
	private List<Integer> validaPricingClasseServico(List<GP_PricingClase> lsPricingClase) {
		List<Integer> classeServicioIds = null;
		if (!lsPricingClase.isEmpty()) {
			classeServicioIds = new ArrayList<Integer>();
			for (GP_PricingClase clase : lsPricingClase) {
				if (clase.getClaseServicio().getClaseservicioId() != -1) {
					classeServicioIds.add(clase.getClaseServicio().getClaseservicioId());
				}
			}
		}
		return classeServicioIds;
	}

}
