<?php
error_reporting(E_ALL);
header("Access-Control-Allow-Methods: POST");
header("Content-Type: application/json; charset=UTF-8");

include_once '../conexion.php';
include_once '../clases/TokenValidator.php';

// Llama la validación antes de cualquier consulta
$usuarioId = TokenValidator::validar($conn);


ini_set('display_errors', 1);
ini_set('log_errors', 1);
ini_set('error_log', 'error_log.txt'); // Guardará errores en este archivo

try {
    $bodyRequest = file_get_contents("php://input");
    $data = json_decode($bodyRequest, true);

    // Si el JSON no se decodifica correctamente, detener y mostrar error
    if ($data === null) {
        die(json_encode(["error" => "JSON inválido", "mensaje" => json_last_error_msg()]));
    }

    if (json_last_error() !== JSON_ERROR_NONE) {
        echo json_encode([
            'status' => 'error',
            'message' => 'Error en el JSON recibido: ' . json_last_error_msg()
        ], JSON_UNESCAPED_UNICODE);
        http_response_code(400);
        exit();
    }

    if (!isset($data['Estado'])) {
        throw new Exception("Falta el campo 'Estado'.");
    }

    $conn->beginTransaction();  // 🔹 Iniciar transacción

    if (!is_array($data['detalle']) || !is_array($data['cuotas']) || !is_array($data['pagos']) || !is_array($data['canje']) || !is_array($data['series'])) {
        echo json_encode([
            'status' => 'error',
            'message' => 'Los campos detalle, cuotas, pagos, canje y series deben ser arrays.'
        ], JSON_UNESCAPED_UNICODE);
        http_response_code(400);
        exit();
    }

    $requiredFields = [
        'Empresa_id', 'DocFiscal_Id', 'NSerie', 'Fecha_Emision', 'Fecha_Traslado', 
        'Fecha_Vcto', 'Razon_Social', 'Direccion', 'Tipo_Documento', 'DocIdentidad', 'NDias', 
        'Moneda', 'Tipo_Cambio', 'Afecto_IGV', 'pIGV', 'IGV', 'Afecto_Dscto', 'pDSCTO', 
        'Descuento', 'Afecto_Percepcion', 'pPercepcion', 'Percepcion', 'Valor_Venta', 
        'Inafecto', 'Exonerada', 'Total_Pagar', 'NGuiaRemision', 'Cancelado', 'ICBPER', 
        'Gratuitas', 'Afecta_Kardex', 'Afecta_Caja', 'Periodo', 'Mes', 'Forma_Pago', 
        'Caja_Id', 'Cliente_Id', 'Empleado_Id', 'Sucursal_Id', 'Observacion', 'a_Cuenta', 
        'Servicio', 'Zona_Id', 'TipoRubro', 'Despacho_Id', 'Tipo_Operacion', 'Operacion', 'Conductor_Id',
        'IdVta_M', 'Estado', 'detalle', 'cuotas', 'pagos',
        'canje', 'series'
    ];
    
    foreach ($requiredFields as $field) {
        if (!isset($data[$field])) {
            echo json_encode([
                'status' => 'error',
                'message' => "Falta el campo '$field'."
            ], JSON_UNESCAPED_UNICODE);
            http_response_code(400);
            exit();
        }
    }

    // Llamar a la función procesar_venta en PostgreSQL
    $sql = "SELECT procesar_despacho(
                :p_empresa_id, :p_docfiscal_id, :p_nserie, :p_fecha_emision, :p_fecha_traslado, :p_fecha_vencimiento,
                :p_nombre, :p_direccion, :p_tipdocident, :p_docidentidad, :p_ndias, :p_moneda, :p_tipo_cambio, :p_afecto_igv, 
                :p_pigv, :p_igv, :p_afect_dscto, :p_pdscto, :p_descuento, :p_afecto_percepcion, :p_ppercepcion, :p_percepcion,
                :p_afecto, :p_inafecto, :p_exonerado, :p_total, :p_guia_remision, :p_cancelado, :p_icbp, :p_gratuitas, 
                :p_afecta_kardex, :p_afecta_caja, :p_periodo, :p_mes, :p_forma_pago_id, :p_caja_id, :p_cliente_id, 
                :p_empleado_id, :p_sucursal_id, :p_observacion, :p_acuenta, :p_servicio, :p_zona_id, :p_tipo_rubro, 
                :p_placa, :p_valor_ref, :p_despacho_id, :p_tipopera, :p_operacion, :p_conductor_id,
                :p_iidvta, :p_estado, :p_detalle, :p_cuotas, :p_pagos, :p_canje, :p_series
            ) AS id_venta";

    $stmt = $conn->prepare($sql);

    $data['Observacion'] = isset($data['Observacion']) ? $data['Observacion'] : '';
    $data['ValorReferencial'] = isset($data['ValorReferencial']) ? $data['ValorReferencial'] : '';

    // Asignar valores a los parámetros
    $stmt->bindValue(':p_empresa_id', $data['Empresa_id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_docfiscal_id', $data['DocFiscal_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_nserie', $data['NSerie'], PDO::PARAM_STR);
    // $stmt->bindValue(':p_ndocumento', $data['NDocumento'], PDO::PARAM_STR);
    $stmt->bindValue(':p_fecha_emision', $data['Fecha_Emision'], PDO::PARAM_STR);
    $stmt->bindValue(':p_fecha_traslado', $data['Fecha_Traslado'], PDO::PARAM_STR);
    $stmt->bindValue(':p_fecha_vencimiento', $data['Fecha_Vcto'], PDO::PARAM_STR);
    $stmt->bindValue(':p_nombre', $data['Razon_Social'], PDO::PARAM_STR);
    $stmt->bindValue(':p_direccion', $data['Direccion'], PDO::PARAM_STR);
    $stmt->bindValue(':p_tipdocident', $data['Tipo_Documento'], PDO::PARAM_INT);
    $stmt->bindValue(':p_docidentidad', $data['DocIdentidad'], PDO::PARAM_STR);
    $stmt->bindValue(':p_ndias', $data['NDias'], PDO::PARAM_INT);
    $stmt->bindValue(':p_moneda', $data['Moneda'], PDO::PARAM_STR);
    $stmt->bindValue(':p_tipo_cambio', $data['Tipo_Cambio'], PDO::PARAM_STR);
    $stmt->bindValue(':p_afecto_igv', filter_var($data['Afecto_IGV'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_pigv', $data['pIGV'], PDO::PARAM_STR);
    $stmt->bindValue(':p_igv', $data['IGV'], PDO::PARAM_STR);
    $stmt->bindValue(':p_afect_dscto', filter_var($data['Afecto_Dscto'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_pdscto', $data['pDSCTO'], PDO::PARAM_STR);
    $stmt->bindValue(':p_descuento', $data['Descuento'], PDO::PARAM_STR);
    $stmt->bindValue(':p_afecto_percepcion', filter_var($data['Afecto_Percepcion'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_ppercepcion', $data['pPercepcion'], PDO::PARAM_STR);
    $stmt->bindValue(':p_percepcion', $data['Percepcion'], PDO::PARAM_STR);
    $stmt->bindValue(':p_afecto', $data['Valor_Venta'], PDO::PARAM_STR);
    $stmt->bindValue(':p_inafecto', $data['Inafecto'], PDO::PARAM_STR);
    $stmt->bindValue(':p_exonerado', $data['Exonerada'], PDO::PARAM_STR);
    $stmt->bindValue(':p_total', $data['Total_Pagar'], PDO::PARAM_STR);
    $stmt->bindValue(':p_guia_remision', $data['NGuiaRemision'], PDO::PARAM_STR);
    $stmt->bindValue(':p_cancelado', $data['Cancelado'], PDO::PARAM_BOOL);
    $stmt->bindValue(':p_icbp', $data['ICBPER'], PDO::PARAM_STR);
    $stmt->bindValue(':p_gratuitas', $data['Gratuitas'], PDO::PARAM_STR);
    $stmt->bindValue(':p_afecta_kardex', filter_var($data['Afecta_Kardex'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_afecta_caja', filter_var($data['Afecta_Caja'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_periodo', $data['Periodo'], PDO::PARAM_STR);
    $stmt->bindValue(':p_mes', $data['Mes'], PDO::PARAM_STR);
    $stmt->bindValue(':p_forma_pago_id', $data['Forma_Pago'], PDO::PARAM_INT);
    $stmt->bindValue(':p_caja_id', $data['Caja_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_cliente_id', $data['Cliente_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_empleado_id', $data['Empleado_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_sucursal_id', $data['Sucursal_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_observacion', $data['Observacion'], PDO::PARAM_STR);
    $stmt->bindValue(':p_acuenta', $data['a_Cuenta'], PDO::PARAM_STR);
    $stmt->bindValue(':p_servicio', filter_var($data['Servicio'] ?? false, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE) ?? false, PDO::PARAM_BOOL);
    $stmt->bindValue(':p_zona_id', $data['Zona_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_tipo_rubro', $data['TipoRubro'], PDO::PARAM_INT);
    $stmt->bindValue(':p_placa', $data['Placa'] = isset($data['Placa']) ? $data['Placa'] : 0);
    $stmt->bindValue(':p_valor_ref', $data['ValorReferencial'], PDO::PARAM_STR);
    $stmt->bindValue(':p_despacho_id', $data['Despacho_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_tipopera', $data['Tipo_Operacion'], PDO::PARAM_INT);
    $stmt->bindValue(':p_operacion', $data['Operacion'], PDO::PARAM_STR);
    $stmt->bindValue(':p_conductor_id', $data['Conductor_Id'], PDO::PARAM_INT);
    $stmt->bindValue(':p_iidvta', $data['IdVta_M'], PDO::PARAM_INT);
    $stmt->bindValue(':p_estado', $data['Estado'], PDO::PARAM_STR);
    $stmt->bindValue(':p_detalle', json_encode($data['detalle']), PDO::PARAM_STR);
    $stmt->bindValue(':p_cuotas', json_encode($data['cuotas']), PDO::PARAM_STR);
    $stmt->bindValue(':p_pagos', json_encode($data['pagos']), PDO::PARAM_STR);
    $stmt->bindValue(':p_canje', json_encode($data['canje']), PDO::PARAM_STR);
    $stmt->bindValue(':p_series', json_encode($data['series']), PDO::PARAM_STR);

    $stmt->execute();
    $resultado = $stmt->fetch(PDO::FETCH_ASSOC);
    $idventa = $resultado['id_venta'];

    $conn->commit();

    echo json_encode([
        "ESTADO" => $idventa > 0 ? "1" : "0",
        "ID" => $idventa ?: "0",
        "MENSAJE" => $idventa > 0 ? "LA VENTA SE PROCESÓ CORRECTAMENTE" : "ERROR AL PROCESAR LA VENTA"
    ], JSON_PRETTY_PRINT);

} catch (PDOException $e) {
    $conn->rollBack();
    echo json_encode([
        "ESTADO" => "0",
        "ID" => "0",
        "MENSAJE" => "ERROR: " . $e->getMessage()
    ], JSON_PRETTY_PRINT);
} finally {
    $conn = null;
}
?>