package com.rjconsultores.ventaboletos.relatorios.impl;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

import com.rjconsultores.ventaboletos.enums.SituacaoVendaPacote;
import com.rjconsultores.ventaboletos.relatorios.utilitarios.DataSource;
import com.rjconsultores.ventaboletos.relatorios.utilitarios.Relatorio;
import com.rjconsultores.ventaboletos.relatorios.utilitarios.RelatorioVendasPacotesBoletosBean;
import com.rjconsultores.ventaboletos.relatorios.utilitarios.RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemBean;
import com.rjconsultores.ventaboletos.utilerias.DateUtil;
import com.rjconsultores.ventaboletos.web.utilerias.NamedParameterStatement;

import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource;

public class RelatorioVendasPacotesBoletos extends Relatorio {

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

	public static final Integer VENDIDOS = 1;
	public static final Integer CANCELADOS = 0;

	private SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy");

	private List<RelatorioVendasPacotesBoletosBean> lsDadosRelatorio;

	private Timestamp fecVendaInicio;
	private Timestamp fecVendaFinal;
	private Timestamp fecPacoteInicio;
	private Timestamp fecPacoteFinal;
	private Integer empresaId;
	private Integer origenId;
	private Integer destinoId;
	private Integer usuarioId;
	private Integer tipoTarifaPacoteId;
	private Integer situacaoBilheteId;

	public RelatorioVendasPacotesBoletos(Map<String, Object> parametros, Connection conexao, final String... nomeSubReporte) throws Exception {
		super(parametros, conexao);

		this.setCustomDataSource(new DataSource(this) {

			@Override
			public void initDados() throws Exception {
				Map<String, Object> parametros = this.relatorio.getParametros();
				fecVendaInicio = parametros.get("fecVendaInicio") != null ? new java.sql.Timestamp(DateUtil.inicioFecha(sdf.parse(parametros.get("fecVendaInicio").toString())).getTime()) : null;
				fecVendaFinal = parametros.get("fecVendaFinal") != null ? new java.sql.Timestamp(DateUtil.fimFecha(sdf.parse(parametros.get("fecVendaFinal").toString())).getTime()) : null;
				fecPacoteInicio = parametros.get("fecPacoteInicio") != null ? new java.sql.Timestamp(DateUtil.inicioFecha(sdf.parse(parametros.get("fecPacoteInicio").toString())).getTime()) : null;
				fecPacoteFinal = parametros.get("fecPacoteFinal") != null ? new java.sql.Timestamp(DateUtil.fimFecha(sdf.parse(parametros.get("fecPacoteFinal").toString())).getTime()) : null;
				empresaId = parametros.get("empresaId") != null && !parametros.get("empresaId").equals("null") ? Integer.valueOf(parametros.get("empresaId").toString()) : null;
				origenId = parametros.get("origenId") != null && !parametros.get("origenId").equals("null") ? Integer.valueOf(parametros.get("origenId").toString()) : null;
				destinoId = parametros.get("destinoId") != null && !parametros.get("destinoId").equals("null") ? Integer.valueOf(parametros.get("destinoId").toString()) : null;
				usuarioId = parametros.get("usuarioId") != null && !parametros.get("usuarioId").equals("null") ? Integer.valueOf(parametros.get("usuarioId").toString()) : null;
				tipoTarifaPacoteId = parametros.get("tipoTarifaPacoteId") != null && !parametros.get("tipoTarifaPacoteId").equals("null") ? Integer.valueOf(parametros.get("tipoTarifaPacoteId").toString()) : null;
				situacaoBilheteId = parametros.get("situacaoBilheteId") != null && !parametros.get("situacaoBilheteId").equals("null") ? Integer.valueOf(parametros.get("situacaoBilheteId").toString()) : null;

				Connection conexao = this.relatorio.getConexao();
				processarVendasPacote(conexao);

				/* Caso o filtro de data de venda de pacote seja informado, não trazer bilhetes avulsos */
				if (fecPacoteInicio == null && fecPacoteFinal == null) {
					if (situacaoBilheteId == null || !CANCELADOS.equals(situacaoBilheteId)) {
						processarVendasAvulsas(conexao);
					}
					if (situacaoBilheteId == null || CANCELADOS.equals(situacaoBilheteId)) {
						processarVendasAvulsasCancelados(conexao);
					}
				}
				processarVendasPacoteTotais();

				setNomeSubReporte(nomeSubReporte);
				setLsDadosRelatorio(lsDadosRelatorio);
			}

		});
	}

	private void processarVendasPacote(Connection conexao) {
		ResultSet rset = null;
		NamedParameterStatement stmt = null;

		try {
			stmt = carregarNamedParameterStatementVendasPacotes(conexao);
			rset = stmt.executeQuery();

			if (lsDadosRelatorio == null) {
				lsDadosRelatorio = new ArrayList<RelatorioVendasPacotesBoletosBean>();
			}

			while (rset.next()) {
				RelatorioVendasPacotesBoletosBean relatorioVendasBoletosBean = carregarRelatorioVendasBoletosBean(rset);
				Integer idx = carregarIndice(relatorioVendasBoletosBean);

				if (idx > -1) {
					relatorioVendasBoletosBean = lsDadosRelatorio.get(idx);
				}

				relatorioVendasBoletosBean.setRelatorioVendasPacotesBoletosItemBeans(carregarItens(rset, relatorioVendasBoletosBean, relatorioVendasBoletosBean.getRelatorioVendasPacotesBoletosItemBeans(), false));

				if (idx > -1) {
					lsDadosRelatorio.set(idx, relatorioVendasBoletosBean);
				} else {
					lsDadosRelatorio.add(relatorioVendasBoletosBean);
				}
			}

		} catch (Exception e) {
			log.error(e.getMessage(), e);
		} finally {
			try {
				if (rset != null) {
					rset.close();
				}
				if (stmt != null) {
					stmt.close();
				}
			} catch (SQLException e) {
				log.error(e.getMessage(), e);
			}
		}

	}

	private List<RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemBean> carregarItens(ResultSet rset, RelatorioVendasPacotesBoletosBean relatorioVendasPacotesBoletosBean, List<RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemBean> itens, Boolean cancelado) throws SQLException {
		RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemBean relatorioVendasPacotesBoletosItemBean = relatorioVendasPacotesBoletosBean.new RelatorioVendasPacotesBoletosItemBean();
		relatorioVendasPacotesBoletosItemBean.setNumruta(rset.getString("numruta"));
		relatorioVendasPacotesBoletosItemBean.setDescruta(rset.getString("descruta"));
		relatorioVendasPacotesBoletosItemBean.setNomconvenio(rset.getString("nomconvenio"));
		relatorioVendasPacotesBoletosItemBean.setDesctipotarifa(rset.getString("desctipotarifa"));
		relatorioVendasPacotesBoletosItemBean.setQtde(rset.getLong("qtde"));
		relatorioVendasPacotesBoletosItemBean.setSimportetaxaembarque(rset.getBigDecimal("simportetaxaembarque"));
		relatorioVendasPacotesBoletosItemBean.setSimportepedagio(rset.getBigDecimal("simportepedagio"));
		relatorioVendasPacotesBoletosItemBean.setSimporteoutros(rset.getBigDecimal("simporteoutros"));
		relatorioVendasPacotesBoletosItemBean.setSimporteseguro(rset.getBigDecimal("simporteseguro"));
		relatorioVendasPacotesBoletosItemBean.setSpreciobase(rset.getBigDecimal("spreciobase"));
		relatorioVendasPacotesBoletosItemBean.setDesconto(rset.getBigDecimal("desconto"));
		relatorioVendasPacotesBoletosItemBean.setSituacao(SituacaoVendaPacote.getSituacaoVendaPacote(rset.getInt("situacao")));
		relatorioVendasPacotesBoletosItemBean.setQtdeImpresso(rset.getInt("qtdeimpresso"));
		relatorioVendasPacotesBoletosItemBean.setTipoVenda(rset.getString("tipovenda"));
		relatorioVendasPacotesBoletosItemBean.setAvulsoCancelado(cancelado);

		if (itens == null) {
			itens = new ArrayList<RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemBean>();
		}
		itens.add(relatorioVendasPacotesBoletosItemBean);

		return itens;
	}

	private Integer carregarIndice(RelatorioVendasPacotesBoletosBean relatorioVendasBoletosBean) {
		Integer idx = -1;
		if (lsDadosRelatorio.contains(relatorioVendasBoletosBean)) {
			idx = lsDadosRelatorio.indexOf(relatorioVendasBoletosBean);
			relatorioVendasBoletosBean = lsDadosRelatorio.get(idx);
		}
		return idx;
	}

	private RelatorioVendasPacotesBoletosBean carregarRelatorioVendasBoletosBean(ResultSet rset) throws SQLException {
		RelatorioVendasPacotesBoletosBean relatorioVendasPacotesBoletosBean = new RelatorioVendasPacotesBoletosBean();
		relatorioVendasPacotesBoletosBean.setDescdestino(rset.getString("destino"));
		relatorioVendasPacotesBoletosBean.setDescorigen(rset.getString("origem"));
		relatorioVendasPacotesBoletosBean.setCvedestino(rset.getString("cvedestino"));
		relatorioVendasPacotesBoletosBean.setCveorigen(rset.getString("cveorigem"));

		return relatorioVendasPacotesBoletosBean;
	}

	private NamedParameterStatement carregarNamedParameterStatementVendasPacotes(Connection conexao) throws SQLException {
		String sql = getSqlVendasPacotes();
		log.info(sql);

		NamedParameterStatement stmt = new NamedParameterStatement(conexao, sql);

		if (fecVendaInicio != null) {
			stmt.setTimestamp("fecVendaInicio", fecVendaInicio);
		}
		if (fecVendaFinal != null) {
			stmt.setTimestamp("fecVendaFinal", fecVendaFinal);
		}
		if (fecPacoteInicio != null) {
			stmt.setTimestamp("fecPacoteInicio", fecPacoteInicio);
		}
		if (fecPacoteFinal != null) {
			stmt.setTimestamp("fecPacoteFinal", fecPacoteFinal);
		}
		if (empresaId != null && empresaId > 0) {
			stmt.setInt("empresaId", empresaId);
		}
		if (origenId != null && origenId > 0) {
			stmt.setInt("origenId", origenId);
		}
		if (destinoId != null && destinoId > 0) {
			stmt.setInt("destinoId", destinoId);
		}
		if (usuarioId != null) {
			stmt.setInt("usuarioId", usuarioId);
		}
		if (tipoTarifaPacoteId != null && tipoTarifaPacoteId > 0) {
			stmt.setInt("tipoTarifaPacoteId", tipoTarifaPacoteId);
		}
		if (situacaoBilheteId != null) {
			stmt.setInt("situacaoPacote", SituacaoVendaPacote.CANCELADO.getShortValue());
		}

		return stmt;
	}

	protected String getSqlVendasPacotes() {
		StringBuilder sQuery = new StringBuilder();

		sQuery.append("SELECT DES.CVEPARADA AS CVEDESTINO, ORI.CVEPARADA AS CVEORIGEM, ORI.DESCPARADA AS ORIGEM, DES.DESCPARADA AS DESTINO, R.NUMRUTA, R.DESCRUTA, PC.NOMCONVENIO, TTP.DESCTIPOTARIFA, VP.SITUACAO, ")
				.append("SUM(CASE WHEN B.MOTIVOCANCELACION_ID = 16 THEN 1 ELSE 0 END) AS QTDEIMPRESSO, ")
				.append("COUNT(TVP.TARIFAVENDAPACOTE_ID) AS QTDE, SUM(T.IMPORTETAXAEMBARQUE) AS SIMPORTETAXAEMBARQUE, SUM(T.IMPORTEPEDAGIO) AS SIMPORTEPEDAGIO, ")
				.append("SUM(NVL(T.IMPORTEOUTROS,0)) AS SIMPORTEOUTROS, SUM(NVL(T.IMPORTESEGURO,0)) AS SIMPORTESEGURO, SUM(NVL(B.PRECIOBASE,0)) AS SPRECIOBASE, ")
				.append("  SUM( ")
				.append("      B.PRECIOBASE+NVL(T.IMPORTETAXAEMBARQUE,0)+NVL(T.IMPORTEPEDAGIO,0)+NVL(T.IMPORTESEGURO,0)+NVL(T.IMPORTEOUTROS,0)- ")
				.append("      B.PRECIOPAGADO-NVL(B.IMPORTETAXAEMBARQUE,0)-NVL(B.IMPORTEPEDAGIO,0)-NVL(B.IMPORTESEGURO,0)-NVL(B.IMPORTEOUTROS,0) ")
				.append("  ) AS DESCONTO, ")
				.append("'PACOTE' AS TIPOVENDA ")
				.append("FROM VENDA_PACOTE VP ")
				.append("INNER JOIN PACOTE P ON P.PACOTE_ID = VP.PACOTE_ID AND P.ACTIVO = 1 ")
				.append("LEFT JOIN TARIFA_VENDA_PACOTE TVP ON TVP.VENDAPACOTE_ID = VP.VENDAPACOTE_ID ")
				.append("INNER JOIN BOLETO B ON B.BOLETO_ID = TVP.BOLETO_ID ")
				.append("LEFT JOIN RUTA R ON R.RUTA_ID = B.RUTA_ID ")
				.append("LEFT JOIN PARADA ORI ON ORI.PARADA_ID = B.ORIGEN_ID ")
				.append("LEFT JOIN PARADA DES ON DES.PARADA_ID = B.DESTINO_ID ")
				.append("LEFT JOIN PACOTE_TARIFA PT ON PT.PACOTETARIFA_ID = TVP.PACOTETARIFA_ID ")
				.append("LEFT JOIN TIPO_TARIFA_PACOTE TTP ON TTP.TIPOTARIFAPACOTE_ID = PT.TIPOTARIFAPACOTE_ID ")
				.append("LEFT JOIN PACOTE_CONVENIO PC ON PC.PACOTECONVENIO_ID = TVP.PACOTECONVENIO_ID AND PC.ACTIVO = 1 ")
				.append("LEFT JOIN VIGENCIA_TARIFA VT ON B.FECHORVENTA BETWEEN VT.FECINICIOVIGENCIA AND VT.FECFINVIGENCIA ")
				.append("LEFT JOIN TARIFA T ON T.RUTA_ID = B.RUTA_ID ")
				.append("                   AND T.DESTINO_ID = B.DESTINO_ID ")
				.append("                   AND T.ORIGEN_ID = B.ORIGEN_ID ")
				.append("                   AND T.CLASESERVICIO_ID = B.CLASESERVICIO_ID ")
				.append("                   AND T.ACTIVO = 1 ")
				.append("                   AND VT.VIGENCIATARIFA_ID = T.VIGENCIATARIFA_ID ")
				.append("                   AND T.ORGAOCONCEDENTE_ID = R.ORGAOCONCEDENTE_ID ")
				.append("WHERE 1=1 ");

		if (fecVendaInicio != null) {
			sQuery.append("AND VP.DATAVENDA >= :fecVendaInicio ");
		}

		if (fecVendaFinal != null) {
			sQuery.append("AND VP.DATAVENDA <= :fecVendaFinal ");
		}

		if (fecPacoteInicio != null) {
			sQuery.append("AND VP.DATAPACOTE >= :fecPacoteInicio ");
		}

		if (fecPacoteFinal != null) {
			sQuery.append("AND VP.DATAPACOTE <= :fecPacoteFinal ");
		}

		if (empresaId != null && empresaId > 0) {
			sQuery.append("AND P.EMPRESA_ID = :empresaId ");
		}

		if (origenId != null && origenId > 0) {
			sQuery.append("AND B.ORIGEN_ID = :origenId ");
		}

		if (destinoId != null && destinoId > 0) {
			sQuery.append("AND B.DESTINO_ID = :destinoId ");
		}

		if (usuarioId != null) {
			sQuery.append("AND VP.USUARIO_ID = :usuarioId ");
		}

		if (tipoTarifaPacoteId != null && tipoTarifaPacoteId > 0) {
			sQuery.append("AND TTP.TIPOTARIFAPACOTE_ID = :tipoTarifaPacoteId ");
		}

		if (situacaoBilheteId != null) {
		}

		if (situacaoBilheteId != null && !CANCELADOS.equals(situacaoBilheteId)) {
			sQuery.append("AND VP.SITUACAO <> :situacaoPacote ");
		}

		if (situacaoBilheteId != null && CANCELADOS.equals(situacaoBilheteId)) {
			sQuery.append("AND VP.SITUACAO = :situacaoPacote ");
		}

		sQuery.append("GROUP BY DES.CVEPARADA, ORI.CVEPARADA, ORI.DESCPARADA, DES.DESCPARADA, R.NUMRUTA, R.DESCRUTA, PC.NOMCONVENIO, TTP.DESCTIPOTARIFA, VP.SITUACAO, 'PACOTE' ")
				.append("ORDER BY DES.CVEPARADA, ORI.CVEPARADA, ORI.DESCPARADA, DES.DESCPARADA, R.NUMRUTA, R.DESCRUTA, PC.NOMCONVENIO, TTP.DESCTIPOTARIFA, VP.SITUACAO, 'PACOTE' ");

		return sQuery.toString();
	}

	private void processarVendasPacoteTotais() {
		List<RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemTotaisBean> totais = new ArrayList<RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemTotaisBean>();
		for (RelatorioVendasPacotesBoletosBean relatorioVendasPacotesBoletosBean : lsDadosRelatorio) {
			if (relatorioVendasPacotesBoletosBean.getRelatorioVendasPacotesBoletosItemBeans() != null) {
				for (RelatorioVendasPacotesBoletosItemBean item : relatorioVendasPacotesBoletosBean.getRelatorioVendasPacotesBoletosItemBeans()) {
					RelatorioVendasPacotesBoletosBean.RelatorioVendasPacotesBoletosItemTotaisBean total = relatorioVendasPacotesBoletosBean.new RelatorioVendasPacotesBoletosItemTotaisBean();
					total.setTrecho(relatorioVendasPacotesBoletosBean.getCveorigen() + "-" + relatorioVendasPacotesBoletosBean.getCvedestino());
					total.setCategoria(item.getDesctipotarifa());
					total.setQtde(0l);
					Integer idx = null;
					if (totais.contains(total)) {
						idx = totais.indexOf(total);
						total = totais.get(idx);
					}
					total.setQtde(total.getQtde() + item.getQtde());

					if (idx == null) {
						totais.add(total);
					} else {
						totais.set(idx, total);
					}
				}
			}
		}
		this.parametros.put("totais", totais);
	}

	@Override
	protected void processaParametros() throws Exception {
	}

	public List<RelatorioVendasPacotesBoletosBean> getLsDadosRelatorio() {
		return lsDadosRelatorio;
	}

	public void setLsDadosRelatorio(List<RelatorioVendasPacotesBoletosBean> lsDadosRelatorio) {
		this.setCollectionDataSource(new JRBeanCollectionDataSource(lsDadosRelatorio));
		this.lsDadosRelatorio = lsDadosRelatorio;
	}

	private void processarVendasAvulsas(Connection conexao) {
		ResultSet rset = null;
		NamedParameterStatement stmt = null;

		try {
			stmt = carregarNamedParameterStatementVendasAvulsas(conexao, false);
			rset = stmt.executeQuery();

			if (lsDadosRelatorio == null) {
				lsDadosRelatorio = new ArrayList<RelatorioVendasPacotesBoletosBean>();
			}

			while (rset.next()) {
				RelatorioVendasPacotesBoletosBean relatorioVendasBoletosBean = carregarRelatorioVendasBoletosBean(rset);
				Integer idx = carregarIndice(relatorioVendasBoletosBean);

				if (idx > -1) {
					relatorioVendasBoletosBean = lsDadosRelatorio.get(idx);
				}

				relatorioVendasBoletosBean.setRelatorioVendasPacotesBoletosItemBeans(carregarItens(rset, relatorioVendasBoletosBean, relatorioVendasBoletosBean.getRelatorioVendasPacotesBoletosItemBeans(), false));

				if (idx > -1) {
					lsDadosRelatorio.set(idx, relatorioVendasBoletosBean);
				} else {
					lsDadosRelatorio.add(relatorioVendasBoletosBean);
				}
			}

		} catch (Exception e) {
			log.error(e.getMessage(), e);
		} finally {
			try {
				if (rset != null) {
					rset.close();
				}
				if (stmt != null) {
					stmt.close();
				}
			} catch (SQLException e) {
				log.error(e.getMessage(), e);
			}
		}

	}

	private NamedParameterStatement carregarNamedParameterStatementVendasAvulsas(Connection conexao, boolean cancelados) throws SQLException {
		String sql = getSqlVendasAvulsos(cancelados);
		log.info(sql);

		NamedParameterStatement stmt = new NamedParameterStatement(conexao, sql);

		if (fecVendaInicio != null) {
			stmt.setTimestamp("fecInicio", fecVendaInicio);
		}
		if (fecVendaFinal != null) {
			stmt.setTimestamp("fecFinal", fecVendaFinal);
		}
		if (fecPacoteInicio != null) {
			stmt.setTimestamp("fecViajeInicio", fecPacoteInicio);
		}
		if (fecPacoteFinal != null) {
			stmt.setTimestamp("fecViajeFinal", fecPacoteFinal);
		}
		if (empresaId != null && empresaId > 0) {
			stmt.setInt("empresaId", empresaId);
		}
		if (origenId != null) {
			stmt.setInt("origenId", origenId);
		}
		if (destinoId != null) {
			stmt.setInt("destinoId", destinoId);
		}

		return stmt;
	}

	protected String getSqlVendasAvulsos(boolean cancelado) {
		StringBuilder sQuery = new StringBuilder();

		sQuery.append("SELECT DES.CVEPARADA AS CVEDESTINO, ORI.CVEPARADA AS CVEORIGEM, ORI.DESCPARADA AS ORIGEM, DES.DESCPARADA AS DESTINO, ")
				.append("CAT.DESCCATEGORIA AS DESCTIPOTARIFA, R.NUMRUTA, R.DESCRUTA, NULL AS SITUACAO, 1 AS QTDEIMPRESSO, NULL AS NOMCONVENIO, 'AVULSO' AS TIPOVENDA, ")
				.append("COUNT(B.BOLETO_ID) AS QTDE, SUM(B.IMPORTETAXAEMBARQUE) AS SIMPORTETAXAEMBARQUE, SUM(B.IMPORTEPEDAGIO) AS SIMPORTEPEDAGIO, ")
				.append("SUM(B.IMPORTEOUTROS) AS SIMPORTEOUTROS, SUM(B.IMPORTESEGURO) AS SIMPORTESEGURO, SUM(B.PRECIOBASE) AS SPRECIOBASE, SUM(NVL(B.DESCUENTOAMPARADO,0)) AS DESCONTO ")
				.append("FROM BOLETO B ")
				.append("LEFT JOIN PARADA ORI ON ORI.PARADA_ID = B.ORIGEN_ID ")
				.append("LEFT JOIN PARADA DES ON DES.PARADA_ID = B.DESTINO_ID ")
				.append("LEFT JOIN CATEGORIA CAT ON CAT.CATEGORIA_ID = B.CATEGORIA_ID ")
				.append("LEFT JOIN RUTA R ON R.RUTA_ID = B.RUTA_ID ")
				.append("WHERE B.ACTIVO = 1 ");

		if (!cancelado) {
			sQuery.append("AND B.INDSTATUSBOLETO = 'V' ")
					.append("AND B.MOTIVOCANCELACION_ID IS NULL ");
		} else {
			sQuery.append("AND B.MOTIVOCANCELACION_ID IS NOT NULL ");
		}

		if (empresaId != null && empresaId > 0) {
			sQuery.append("AND B.EMPRESACORRIDA_ID = :empresaId ");
		}

		if (origenId != null) {
			sQuery.append("AND B.ORIGEN_ID = :origenId ");
		}

		if (destinoId != null) {
			sQuery.append("AND B.DESTINO_ID = :destinoId ");
		}

		if (fecVendaInicio != null) {
			sQuery.append("AND B.FECHORVENTA >= :fecInicio ");
		}

		if (fecVendaFinal != null) {
			sQuery.append("AND B.FECHORVENTA <= :fecFinal ");
		}

		if (fecPacoteInicio != null) {
			sQuery.append("AND B.FECHORVIAJE >= :fecViajeInicio ");
		}

		if (fecPacoteFinal != null) {
			sQuery.append("AND B.FECHORVIAJE <= :fecViajeFinal ");
		}

		sQuery.append("GROUP BY DES.CVEPARADA, ORI.CVEPARADA, ORI.DESCPARADA, DES.DESCPARADA, CAT.DESCCATEGORIA, R.NUMRUTA, R.DESCRUTA, NULL, 1, NULL, 'AVULSO' ")
				.append("ORDER BY DES.CVEPARADA, ORI.CVEPARADA, ORI.DESCPARADA, DES.DESCPARADA, CAT.DESCCATEGORIA, R.NUMRUTA, R.DESCRUTA, NULL, 1, NULL, 'AVULSO' ");

		return sQuery.toString();
	}

	private void processarVendasAvulsasCancelados(Connection conexao) {
		ResultSet rset = null;
		NamedParameterStatement stmt = null;

		try {
			stmt = carregarNamedParameterStatementVendasAvulsas(conexao, true);
			rset = stmt.executeQuery();

			if (lsDadosRelatorio == null) {
				lsDadosRelatorio = new ArrayList<RelatorioVendasPacotesBoletosBean>();
			}

			while (rset.next()) {
				RelatorioVendasPacotesBoletosBean relatorioVendasBoletosBean = carregarRelatorioVendasBoletosBean(rset);
				Integer idx = carregarIndice(relatorioVendasBoletosBean);

				if (idx > -1) {
					relatorioVendasBoletosBean = lsDadosRelatorio.get(idx);
				}

				relatorioVendasBoletosBean.setRelatorioVendasPacotesBoletosItemBeansCancelados(carregarItens(rset, relatorioVendasBoletosBean, relatorioVendasBoletosBean.getRelatorioVendasPacotesBoletosItemBeansCancelados(), true));

				if (idx > -1) {
					lsDadosRelatorio.set(idx, relatorioVendasBoletosBean);
				} else {
					lsDadosRelatorio.add(relatorioVendasBoletosBean);
				}
			}

		} catch (Exception e) {
			log.error(e.getMessage(), e);
		} finally {
			try {
				if (rset != null) {
					rset.close();
				}
				if (stmt != null) {
					stmt.close();
				}
			} catch (SQLException e) {
				log.error(e.getMessage(), e);
			}
		}

	}

}
