package com.fp.frontend.controller.armas.solicitud;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;

import javax.annotation.PostConstruct;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ManagedProperty;
import javax.faces.bean.ViewScoped;
import javax.faces.context.FacesContext;

import org.apache.commons.io.FilenameUtils;
import org.primefaces.event.FileUploadEvent;
import org.primefaces.model.UploadedFile;

import com.fp.common.helper.Constant;
import com.fp.dto.Request;
import com.fp.dto.Response;
import com.fp.dto.query.DtoQuery;
import com.fp.dto.save.DtoSave;
import com.fp.frontend.controller.AbstractController;
import com.fp.frontend.controller.alfresco.AlfrescoController;
import com.fp.frontend.controller.pcustomer.PersonDetailController;
//import com.fp.frontend.controller.pgeneral.menu.MenuController;
import com.fp.frontend.helper.MessageHelper;
import com.fp.frontend.utility.MsgControlArmas;
import com.fp.frontend.utility.MsgGeneral;
import com.fp.frontend.utility.Utilidades;
import com.fp.persistence.parmas.param.TarmCentroControl;
import com.fp.persistence.parmas.soli.TarmCertificadoFiscalia;
import com.fp.persistence.pcustomer.gene.TcustPersonDetail;
import com.fp.persistence.pgeneral.safe.TsafeUserDetail;

/**
 * Clase controladora para subir solicitudes de Certificados de Fiscalia.
 *
 * @author Manuel Cepeda.
 * @version 2.1
 */
@SuppressWarnings("serial")
@ManagedBean
@ViewScoped
public class SolicitudCertificadoController extends AbstractController<TarmCertificadoFiscalia> {

//	@ManagedProperty(value = "#{menuController}")
//	private MenuController menuController;
    /**
     * Propiedad que premite controlar operaciones de cargar archivos al
     * Alfresco
     */
    @ManagedProperty(value = "#{alfrescoController}")
    private AlfrescoController alfrescoController;

    /**
     * codigo de la provincia del usuario logeado
     */
    private String cprovincia;

    /**
     * Variable que nos permite cargar el comprobante de deposito al Alfresco
     */
    private UploadedFile uploadedFile;
    private TsafeUserDetail tsafeUserDetail;
    private String cargado;
    /**
     * Deshabilita la pantalla despu&eacute;s de grabar la solicitud
     */
    private boolean deshabilitarPantalla;
    /**
     * Indica si el flujo ya fue iniciado, sirve para controlar que no iniciar
     * el flujo mas de una vez.
     */
    private boolean flujoiniciado;
    private boolean grabarInformacion;

    public SolicitudCertificadoController() throws Exception {
        super(TarmCertificadoFiscalia.class);
    }

    /**
     * M&eacute;todo que se ejecuta despu&eacute;s del constructor
     */
    @PostConstruct
    private void postconstruct() {
        this.init();
        super.startQuery();
    }

    /**
     * Inicializa valores del controlador
     */
    private void init() {
        try {
            recperpage = 15; // Cambiar al # reg a mirar.
            lrecord = new ArrayList<>();
            record = new TarmCertificadoFiscalia();
            beanalias = "CERTIFICADOFISCALIA";
            tsafeUserDetail = (TsafeUserDetail) FacesContext.getCurrentInstance().getExternalContext().getSessionMap().get("TSAFEUSERDETAIL");
            record.setNrsolicitud(null);
            TarmCentroControl centroControl = Utilidades.obtenerCentroControl();
            cprovincia = centroControl.getProvincecode();
            grabarInformacion = true;
            flujoiniciado = true;
        } catch (Exception e) {
            MessageHelper.setMessageError(e);
        }
    }

    @SuppressWarnings("unchecked")
    @Override
    protected void querydatabase() {
        try {
            if (deshabilitarPantalla) {
                return;
            }
            DtoQuery dto = super.getDtoQuery(true);
            dto.setOrderby("pk desc");
            HashMap<String, DtoQuery> mtables = new HashMap<String, DtoQuery>();
            mtables.put(this.beanalias, dto); // permite adicionar mas de una tabla.

            Request request = this.callerhelper.getRequest();
            if (request.containsKey("querytype")) {
                request.remove("querytype");
            }
            request.setQueryTables(mtables);
            Response resp = this.callerhelper.executeQuery(request);

            if (resp.getResponseCode().compareTo(Response.RESPONSE_OK) != 0) {
                this.lrecord = new ArrayList<TarmCertificadoFiscalia>();
                MessageHelper.setMessageError(resp);
            } else {
                this.lrecord = (List<TarmCertificadoFiscalia>) resp.get(this.beanalias);
                if (lrecord != null && !lrecord.isEmpty()) {
                    record = lrecord.get(0);
                    super.postQuery(this.lrecord);
                }

            }
        } catch (Throwable e) {
            MessageHelper.setMessageError(e);
        }
    }

    @Override
    public void next() throws Exception {
        // TODO Auto-generated method stub
        super.next();
    }

    @Override
    public void save() {
        try {
            if (grabarInformacion) {
                return;
            }
            DtoSave dtosave = super.getDtoSave();
            dtosave.setReturnpk(true); // Para que el core devuelva el pk de los registros nuevos.
            HashMap<String, DtoSave> msave = new HashMap<String, DtoSave>();
            uploadCertificado();
            if (tsafeUserDetail != null) {
                record.setPersoncode(tsafeUserDetail.getPk().getPersoncode());
            }
            Request request = callerhelper.getRequest();
            msave.put(this.beanalias, dtosave);
            request.setSaveTables(msave);
            Response resp = callerhelper.executeSave(request);
            if (resp.getResponseCode().compareTo(Response.RESPONSE_OK) == 0) {
                this.postCommit(resp);
                deshabilitarPantalla = Boolean.TRUE;
                flujoiniciado = Boolean.FALSE;
                grabarInformacion = Boolean.TRUE;
                MessageHelper.setMessageInfo(resp);
//                init();
            } else {
                //MessageHelper.setMessageError(resp);                
            }
        } catch (Throwable e) {
            //MessageHelper.setMessageError(e);
        }
    }

    /**
     * M&eacute;todo para el inicio de flujo
     */
    public void iniciarFlujo() {
        try {
            if (flujoiniciado) {
                return;
            }
            Request request = callerhelper.getRequest();
            super.cleanRequest(request);
            request.modifiedData().put("isnew", "Y");
            request.modifiedData().put("csolicitud", record.getNrsolicitud());
            request.modifiedData().put("numerosolicitud", record.getNrsolicitud());
            request.modifiedData().put("cprovincia", cprovincia);
            request.modifiedData().put("xpath", record.getXpath());

            request.setLogsolicitude(record.getNrsolicitud());

            Response resp = callerhelper.executeSave(request);
            if (resp.getResponseCode().compareTo(Response.RESPONSE_OK) == 0) {
                this.setShowRow(true);

                deshabilitarPantalla = Boolean.FALSE;
                flujoiniciado = Boolean.TRUE;
                grabarInformacion = Boolean.TRUE;

                MessageHelper.setMessageInfo(resp, MsgGeneral.getProperty("msg_initFlow") + " SOLICITUD: " + record.getNrsolicitud());

//                RequestContext.getCurrentInstance().execute("Maia.refreshusertasks()");
            } else {
                MessageHelper.setMessageError(resp);
            }
        } catch (Throwable e) {
            MessageHelper.setMessageError(e);
        }
    }

    public void updateAutorizacion() throws Exception {
        super.update();
    }

    /**
     * M&eacute;todo que se ejecuta al carga edici&oacute;n
     *
     * @throws Exception
     */
    public void loadEdit() throws Exception {
//    	setSelectedDocumentos(record.getDocumento().split(", "));
    }

    @Override
    public void create() throws Exception {
        super.create();
        if (record != null) {
            record.setFcreacion(new Date());
            if (tsafeUserDetail != null) {
                TcustPersonDetail personDetail = PersonDetailController.find(tsafeUserDetail.getPk().getPersoncode().toString());
                if (personDetail != null) {
                    record.setNombresolicitante(personDetail.getName());
                }
            }
            try {
                obtenerSecuencialSolicitud();
            } catch (Throwable e) {
                e.printStackTrace();
            }
            uploadedFile = null;
            setCargado(Constant.STR_N);
            setGrabarInformacion(true);
            setFlujoiniciado(false);
        }
    }

    public void update(TarmCertificadoFiscalia bean) throws Exception {
        record = bean;
        updateAutorizacion();
    }

    public void actualizar(TarmCertificadoFiscalia arma) throws Exception {
        record = arma;
        super.update();
    }

    /**
     * Permite obtener el Archivo previamente cargado en la pagina
     *
     * @param event
     */
    public void handleUpload(FileUploadEvent event) {
        uploadedFile = event.getFile();
        setCargado(Constant.STR_Y);
    }

    /**
     * M&eacute;todo de carga de archivos en Alfresco
     *
     * @param event
     */
    public void uploadCertificado() {
        try {
            if (uploadedFile != null && uploadedFile.getFileName() != null && !"".equals(uploadedFile.getFileName())) {
                String xPathLocation = getRutaDocumentoCertificadoBase() + "/cm:" + record.getNrsolicitud();
                String nombreArchivo = "Certificado_01." + FilenameUtils.getExtension(uploadedFile.getFileName());
                if (alfrescoController.uploadFile(uploadedFile.getInputstream(), nombreArchivo, xPathLocation)) {
                    setCargado(Constant.STR_Y);
                    record.setXpath(xPathLocation + "/cm:" + nombreArchivo);

                }
            }
        } catch (Throwable e) {
            MessageHelper.setMessageError(e);
        }
    }

    /**
     * Retorna la ruta base donde se almacenara dicho archivo
     *
     * @return
     */
    public String getRutaDocumentoCertificadoBase() {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(new Date());
        StringBuilder ruta = new StringBuilder("cm:Certificados");
        ruta = ruta.append("/cm:A-").append(calendar.get(Calendar.YEAR));
        ruta = ruta.append("/cm:M-").append((calendar.get(Calendar.MONTH) + 1) <= 9 ? "0" + (calendar.get(Calendar.MONTH) + 1) : (calendar.get(Calendar.MONTH) + 1));
        return ruta.toString();
    }

    /**
     * Arma la petici&oacute;n al core para solicitar un n&uacute;mero de
     * secuencial para la solicitud antes de guardarla
     *
     * @throws Throwable
     */
    private void obtenerSecuencialSolicitud() throws Throwable {
        Request request = callerhelper.getRequest();
        DtoQuery dtoQuery = super.getDtoQuery(true);
        HashMap<String, DtoQuery> mapQuery = new HashMap<String, DtoQuery>();
        mapQuery.put(beanalias, dtoQuery);
        request.put("querytype", "T");
        request.setQueryTables(mapQuery);
        Response response = callerhelper.executeQuery(request);
        if (response.getResponseCode().compareTo(Response.RESPONSE_OK) != 0) {
            MessageHelper.setMessageError(response);
        } else {
            getRecord().setNrsolicitud(response.get("SECUENCIALCERTIFICADOFISCAL").toString());
        }
    }

    /**
     * Metodod que devuelve un CertificadoFiscalia por el codigo de solicitud
     *
     * @param codigoSolicitud
     * @return TarmCertificadoFiscalia
     */
    public static TarmCertificadoFiscalia findPorSolicitud(String codigoSolicitud) {
        try {
            if (codigoSolicitud == null || codigoSolicitud.isEmpty()) {
                return null;
            }
            SolicitudCertificadoController cc = new SolicitudCertificadoController();
            cc.init();
            cc.recperpage = 300;
            cc.addFilter("nrsolicitud", codigoSolicitud);
            cc.querydatabase();
            if (cc.record != null) {
                return cc.record;
            }
            return null;
        } catch (Throwable e) {
            MessageHelper.setMessageError(e);
            return null;
        }
    }

    @Override
    public void update() throws Exception {
        grabarInformacion = Boolean.FALSE;
        flujoiniciado = Boolean.TRUE;
        deshabilitarPantalla = Boolean.TRUE;
        super.update();
    }

//	public MenuController getMenuController() {
//		return menuController;
//	}
//
//	public void setMenuController(MenuController menuController) {
//		this.menuController = menuController;
//	}
    /**
     * @return the uploadedFile
     */
    public UploadedFile getUploadedFile() {
        return uploadedFile;
    }

    /**
     * @param uploadedFile the uploadedFile to set
     */
    public void setUploadedFile(UploadedFile uploadedFile) {
        this.uploadedFile = uploadedFile;
    }

    /**
     * @return the alfrescoController
     */
    public AlfrescoController getAlfrescoController() {
        return alfrescoController;
    }

    /**
     * @param alfrescoController the alfrescoController to set
     */
    public void setAlfrescoController(AlfrescoController alfrescoController) {
        this.alfrescoController = alfrescoController;
    }

    /**
     * @return the cargado
     */
    public String getCargado() {
        return cargado;
    }

    /**
     * @param cargado the cargado to set
     */
    public void setCargado(String cargado) {
        this.cargado = cargado;
    }

    public boolean isDeshabilitarPantalla() {
        return deshabilitarPantalla;
    }

    public void setDeshabilitarPantalla(boolean deshabilitarPantalla) {
        this.deshabilitarPantalla = deshabilitarPantalla;
    }

    public boolean isFlujoiniciado() {
        return flujoiniciado;
    }

    public void setFlujoiniciado(boolean flujoiniciado) {
        this.flujoiniciado = flujoiniciado;
    }

    public String getCprovincia() {
        return cprovincia;
    }

    public void setCprovincia(String cprovincia) {
        this.cprovincia = cprovincia;
    }

    /**
     * @return the grabarInformacion
     */
    public boolean isGrabarInformacion() {
        return grabarInformacion;
    }

    /**
     * @param grabarInformacion the grabarInformacion to set
     */
    public void setGrabarInformacion(boolean grabarInformacion) {
        this.grabarInformacion = grabarInformacion;
    }

}
