<?php
	// ini_set('display_errors', 1);
    // ini_set('display_startup_errors', 1);
    error_reporting(E_ALL ^ E_NOTICE ^ E_DEPRECATED);
	session_start();
	

	if (!isset($_SESSION['valor_coin'])) {
		echo '<h3>Error al obtener el precio del coin</h3><h4>Vuelva hacia atrás e intente realizar de nuevo la operación</h4>';
		exit;
	}
    
    ob_start();

	// Llamo a la librería de cryptos por si se necesita
	require_once 'vendor/autoload.php';
	use CoinbaseCommerce\ApiClient;
	use CoinbaseCommerce\Resources\Charge;
	
	// Declaraciones use para MercadoPago SDK v3
	use MercadoPago\MercadoPagoConfig;
	use MercadoPago\Client\Preference\PreferenceClient;

	if (isset($_POST['module'])) {
		$indexing = 1;
		include 'functions/func.php';
		include 'configs.php'; 

		$errores = 0;
		$error_text = '';

		$bp_key=uniqid(); // Código único de seguimiento

		// Precios del coin almacenados en una session
		$valor_peso = $_SESSION['valor_coin']['peso'];
		$valor_dolar = $_SESSION['valor_coin']['dolar'];

		switch (htmlentities($_POST['module'])) {
			case 'checkout_no_auth':
				// 🛡️ SANITIZACIÓN AVANZADA DE VARIABLES
				$nombre = vCode($_POST['recipient']);
				$pay_method = vCode($_POST['payment_method']);
				$cantidad = intval(vCode($_POST['sum'])); // Forzar entero
				$sum_usd = floatval($valor_dolar * $cantidad); // Forzar float
				$loc = 'INVENTORY';
				$moneda_id = '9623';

				// 🔍 VALIDACIONES DE SEGURIDAD MEJORADAS
				
				// 1️⃣ Validar que el nombre no esté vacío y tenga formato válido
				if (empty($nombre) || strlen($nombre) < 2 || strlen($nombre) > 50) {
					$errores = 1;
					$error_text = 'nombre_invalido';
					goto error;
				}
				
				// 2️⃣ Validar método de pago permitido
				$metodos_permitidos = ['paypal', 'mercadopago', 'crypto', 'kamipay'];
				if (!in_array($pay_method, $metodos_permitidos)) {
					$errores = 1;
					$error_text = 'metodo_pago_invalido';
					goto error;
				}
				
				// 3️⃣ Validar cantidad (mín 1, máx 10000)
				if (!is_numeric($cantidad) || $cantidad < 1 || $cantidad > 10000) {
					$errores = 1;
					$error_text = 'cantidad_invalida';
					goto error;
				}
				
				// 4️⃣ 💰 VALIDACIÓN MÍNIMO $1 USD PARA PAYPAL
				if ($pay_method == 'paypal' && $sum_usd < 1.00) {
					$errores = 1;
					$error_text = 'monto_minimo_paypal';
					goto error;
				}
				
				// 5️⃣ Validar que el precio USD no sea negativo o excesivo
				if ($sum_usd < 0 || $sum_usd > 10000) {
					$errores = 1;
					$error_text = 'precio_invalido';
					goto error;
				}

				// 🛡️ CONSULTA SQL PROTEGIDA CON PREPARED STATEMENTS
				try {
					$stmt = $pdo->prepare("SELECT obj_id, char_name FROM characters WHERE char_name = ? LIMIT 1");
					$stmt->execute([$nombre]);
					$personaje_data = $stmt->fetch(PDO::FETCH_ASSOC);
					
					if (!$personaje_data) {
						$errores = 1;
						$error_text = 'personaje_no_existe';
						goto error;
					}
					
					// Validar que el personaje tenga un obj_id válido
					if (empty($personaje_data['obj_id']) || !is_numeric($personaje_data['obj_id'])) {
						$errores = 1;
						$error_text = 'personaje_datos_invalidos';
						goto error;
					}
					
				} catch (PDOException $e) {
					error_log("Error en consulta SQL don_save.php: " . $e->getMessage());
					$errores = 1;
					$error_text = 'error_base_datos';
					goto error;
				}
				
					if ($errores==0) {
						// Validar precio calculado
							$precio_por_coin = 0.10;
							$precio_esperado = $cantidad * $precio_por_coin;

						// Proceso de pogo
						if ($pay_method=='mercadopago') {
							if (isset($mp_access_token)) {
								require ('mp_api/mercado_pago_api/autoload.php');
								
								MercadoPagoConfig::setAccessToken($mp_access_token);
								
								// Crea un cliente de preferencia
								$client = new PreferenceClient();

								// Crear la preferencia usando la nueva API v3
								$preference_data = [
									"back_urls" => [
										"success" => $mp_success.'?pay_method=mp',
										"failure" => $mp_cancel.'?pay_method=mp',
										"pending" => $mp_cancel.'?pay_method=mp'
									],
									"auto_return" => "approved",
									"items" => [[
										"title" => "Donación a personaje $nombre",
										"id" => $nombre,
										"quantity" => $cantidad,
										"currency_id" => 'ARS',
										"unit_price" => $valor_peso
									]],
									"payment_methods" => [
										"excluded_payment_types" => [
											["id" => "ticket"]
										]
									],
									"external_reference" => $nombre,
									"notification_url" => $mp_ipn
								];

								try {
									$preference = $client->create($preference_data);
									
									if (!empty($preference->init_point)) {
										echo "<script type='text/javascript'>
											document.location.href = '".$preference->init_point."';
										</script>";
									} else {
										$errores = 1;
										$error_text = '';
										echo 'Error al obtener la ruta de redirección de Mercado Pago. <br>Puede que el token sea incorrecto o no se encuentre en configs.php
										<br>#'.substr($mp_access_token, -7);
										goto error;
									}
								} catch (Exception $e) {
									$errores = 1;
									$error_text = '';
									echo 'Error al crear la preferencia de Mercado Pago: ' . $e->getMessage();
									goto error;
								}
							}else {
								$errores = 1;
								$error_text = 'token';
								goto error;
							}
						}elseif ($pay_method=='paypal'){
							// 🔒 VALIDACIÓN FINAL PARA PAYPAL
							if ($sum_usd < 1.00) {
								$errores = 1;
								$error_text = 'monto_minimo_paypal';
								goto error;
							}
							
							if (abs($sum_usd - $precio_esperado) > 0.01) {
								error_log("Price validation failed: Expected=$precio_esperado, Received=$sum_usd, IP=" . ($_SERVER['REMOTE_ADDR'] ?? 'unknown'));
								$errores = 1;
								$error_text = 'precio_incoherente';
								goto error;
							}
							
							// Generar identificador de transacción
							$secret_key = 'L2_SECRET_2024_' . md5($email_paypal); // Clave basada en email PayPal
							$security_token = hash_hmac('sha256', 
								$nombre . '|' . $cantidad . '|' . $sum_usd . '|' . time() . '|' . $_SERVER['REMOTE_ADDR'], 
								$secret_key
							);
							
							// Preparar datos para envío
							$nombre_safe = htmlspecialchars($nombre, ENT_QUOTES, 'UTF-8');
							$cantidad_safe = intval($cantidad);
							$sum_usd_safe = number_format($sum_usd, 2, '.', '');
							
							// Almacenar datos de transacción
							$txn_data = [
								'personaje' => $nombre_safe,
								'cantidad' => $cantidad_safe,
								'precio' => $sum_usd_safe,
								'timestamp' => time(),
								'ip' => $_SERVER['REMOTE_ADDR'] ?? 'unknown'
							];
							
							$txn_file = sys_get_temp_dir() . '/paypal_txn_' . $security_token . '.json';
							file_put_contents($txn_file, json_encode($txn_data), LOCK_EX);
							
							// URL PayPal
							$paypalUrl = ($paypal_mode==0) ? 'https://www.sandbox.paypal.com/cgi-bin/webscr' : 
							'https://www.paypal.com/cgi-bin/webscr';
							?>
								<form name="myform" action="<?php echo htmlspecialchars($paypalUrl, ENT_QUOTES, 'UTF-8'); ?>" method="post" target="_top">
									<input type="hidden" name="cmd" value="_xclick">
									<input type="hidden" name="cancel_return" value="<?php echo htmlspecialchars($paypal_cancel.'?pay_method=paypal', ENT_QUOTES, 'UTF-8'); ?>">
									<input type="hidden" name="return" value="<?php echo htmlspecialchars($paypal_success.'&pay_method=paypal', ENT_QUOTES, 'UTF-8'); ?>">
									<input type="hidden" name="business" value="<?php echo htmlspecialchars($email_paypal, ENT_QUOTES, 'UTF-8'); ?>">
									<input type="hidden" name="lc" value="C2">
									<input type="hidden" name="item_name" value="<?php echo $nombre_safe; ?>">
									<input type="hidden" name="item_number" value="<?php echo $security_token; ?>">
									<input type="hidden" name="quantity" value="1">
									<input type="hidden" name="amount" value="<?php echo $sum_usd_safe; ?>">
									<input type='hidden' name="notify_url" value="<?php echo htmlspecialchars($paypal_ipn, ENT_QUOTES, 'UTF-8'); ?>">
									<input type="hidden" name="currency_code" value="USD">
									<input type="hidden" name="button_subtype" value="services">
									<input type="hidden" name="no_note" value="0">
									<input type="hidden" name="custom" value="<?php echo hash('sha256', $security_token . $sum_usd_safe . date('Y-m-d')); ?>">
								</form>
								<script type="text/javascript">
									window.history.replaceState({}, document.title, "<?=$url_pg?>" + "donaciones.php");
									document.myform.submit();
								</script>
							<?php
						}elseif ($pay_method=='crypto'){
							// Aquí iría la integración con Coinbase Commerce u otro proveedor de criptomonedas
							$coinbaseKey = 'df1111c6-e680-473e-bb2e-eb28b39cbacf';
							ApiClient::init($coinbaseKey);

							// 🔒 VALIDACIÓN FINAL
							if ($sum_usd < 1.00) {
								$errores = 1;
								$error_text = 'monto_minimo_crypto';
								goto error;
							}
							
							if (abs($sum_usd - $precio_esperado) > 0.01) {
								error_log("Price validation failed: Expected=$precio_esperado, Received=$sum_usd, IP=" . ($_SERVER['REMOTE_ADDR'] ?? 'unknown'));
								$errores = 1;
								$error_text = 'precio_incoherente';
								goto error;
							}
							
							// Generar identificador de transacción
							$secret_key = 'L2_SECRET_2024_' . md5($coinbaseKey); // Clave basada en el token de coinbase key
							$security_token = hash_hmac('sha256', 
								$nombre . '|' . $cantidad . '|' . $sum_usd . '|' . time() . '|' . $_SERVER['REMOTE_ADDR'], 
								$secret_key
							);
							
							// Preparar datos para envío
							$nombre_safe = htmlspecialchars($nombre, ENT_QUOTES, 'UTF-8');
							$cantidad_safe = intval($cantidad);
							$sum_usd_safe = number_format($sum_usd, 2, '.', '');

							$txn_file = sys_get_temp_dir() . '/crypto_txn_' . $security_token . '.json';
							file_put_contents($txn_file, json_encode($txn_data), LOCK_EX);

							$idTransaccion = uniqid(); // ID único para la transacción
							
							$cargo = new Charge([
								'name' => $nombre_safe,
								'description' => 'Donaci&oacute;n a personaje '.$nombre,
								'local_price' => [
									'amount' => number_format($sum_usd_safe, 2, '.', ''),
									'currency' => 'USD'
								],
								'metadata' => [
									'customer_id' => 'id-'.$idTransaccion,
									'customer_name' => $nombre_safe,
									'order_id' => 'oid-'.$idTransaccion,
									'cantidad' => number_format($cantidad_safe, 0, '.', ''),
        							'precio_unitario' => number_format($precio_por_coin, 2, '.', '')
								],
								'pricing_type' => 'fixed_price'
							]);

							try {
								$cargo->save();
								echo "Id de compra: ".$cargo->id."<br>"; // ID of the created charge
								echo "URL de pago: <a href='".$cargo->hosted_url."' target='_blank'>PAGAR</a><br>"; // URL to the checkout page
								?>
									<script type="text/javascript">
										window.location.href = "<?= htmlspecialchars($cargo->hosted_url, ENT_QUOTES, 'UTF-8') ?>";
									</script>
								<?php
							} catch (\Exception $th) {
								echo "Error: " . $th->getMessage();
							}

						} elseif ($pay_method == 'kamipay') {
							// 🇧🇷 KAMIPAY (PIX BRASIL) - NUEVO MÉTODO DE PAGO
							require_once 'kamipay/KamiPayAPI.php';
							
							// Validación mínima para KamiPay (equivalente a ~$3 USD en BRL)
							$minimum_brl = 15.0; // Mínimo 15 BRL
							
							// Obtener cotización actual
							$kamiPay = new KamiPayAPI($kamipay_mode == 0);
							$oracle = $kamiPay->getOracle('USDTBRL', 'charge', $sum_usd);
							
							if (!$oracle) {
								$errores = 1;
								$error_text = 'kamipay_cotizacion_error';
								goto error;
							}
							
							$amount_brl = $oracle['total_brl'];
							$amount_usdt = $oracle['total_usdt'];
							$rate = $oracle['rate'];
							
							// Validar monto mínimo
							if ($amount_brl < $minimum_brl) {
								$errores = 1;
								$error_text = 'kamipay_monto_minimo';
								goto error;
							}
							
							// Crear referencia externa única
							$external_reference = 'L2JADE_' . $nombre_safe . '_' . time() . '_' . $cantidad_safe;
							
							// Crear QR PIX
							$pixData = $kamiPay->createPixQR(
								$kamipay_wallet_address,
								$amount_brl,
								900, // 15 minutos de expiración
								$external_reference
							);
							
							if (!$pixData) {
								$errores = 1;
								$error_text = 'kamipay_qr_error';
								goto error;
							}
							
							// Guardar datos de transacción en base de datos
							try {
								$stmt = $pdo->prepare("INSERT INTO kamipay_transactions (
									operation_id, character_name, amount_jc, amount_brl, amount_usdt, 
									rate, external_reference, emv_code, status, created_at, expires_at
								) VALUES (?, ?, ?, ?, ?, ?, ?, ?, 'pending', NOW(), DATE_ADD(NOW(), INTERVAL 15 MINUTE))");
								
								$stmt->execute([
									$pixData['operation_id'],
									$nombre_safe,
									$cantidad_safe,
									$amount_brl,
									$amount_usdt,
									$rate,
									$external_reference,
									$pixData['emv']
								]);
								
								error_log("KamiPay transaction created: " . $pixData['operation_id']);
								
							} catch (PDOException $e) {
								error_log("Error saving KamiPay transaction: " . $e->getMessage());
								$errores = 1;
								$error_text = 'kamipay_database_error';
								goto error;
							}
							
							// Redirigir a página de pago PIX
							$redirect_url = "kamipay/pix_payment.php?op=" . urlencode($pixData['operation_id']) . 
										   "&ref=" . urlencode($external_reference);
							?>
							<script type="text/javascript">
								window.location.href = "<?= htmlspecialchars($redirect_url, ENT_QUOTES, 'UTF-8') ?>";
							</script>
							<?php
							exit();

						}
					}
				break;
		}

		// 🚨 MANEJO MEJORADO DE ERRORES
		if ($errores==1) {
			error:
			$error_text = vCode($error_text);
			
			// 📝 Mapear códigos de error a mensajes amigables
			$mensajes_error = [
				'nombre_invalido' => 'El nombre del personaje debe tener entre 2 y 50 caracteres',
				'metodo_pago_invalido' => 'Método de pago no válido',
				'cantidad_invalida' => 'La cantidad debe ser un número entre 1 y 10,000',
				'monto_minimo_paypal' => 'El monto mínimo para PayPal es de $1.00 USD',
				'precio_invalido' => 'El precio calculado no es válido',
				'personaje_no_existe' => 'El personaje no existe en el servidor',
				'personaje_datos_invalidos' => 'Los datos del personaje no son válidos',
				'error_base_datos' => 'Error temporal en la base de datos. Intente nuevamente',
				'token' => 'Error de configuración del sistema de pagos',
				'cantidad' => 'La cantidad ingresada no es válida',
				'nombre' => 'El personaje especificado no existe',
				'precio_incoherente' => 'El precio calculado no es coherente con la cantidad',
				// KamiPay errors
				'kamipay_cotizacion_error' => 'No se pudo obtener la cotización PIX. Intente nuevamente',
				'kamipay_monto_minimo' => 'El monto mínimo para PIX es de 15 BRL (aproximadamente $3 USD)',
				'kamipay_qr_error' => 'No se pudo generar el código PIX. Intente nuevamente',
				'kamipay_database_error' => 'Error al procesar la transacción PIX. Contacte al soporte'
			];
			
			// Obtener mensaje amigable o usar el código de error
			$mensaje_final = isset($mensajes_error[$error_text]) ? 
							$mensajes_error[$error_text] : 
							$error_text;

			if (empty($error_text)) exit;
			
			// 📋 Log del error para debugging (sin datos sensibles)
			error_log("Error en don_save.php: Código=$error_text, IP=" . ($_SERVER['REMOTE_ADDR'] ?? 'unknown'));
			
			header("Location: donaciones.php?error=".urlencode($mensaje_final));
			exit;
		}

		$pdo=null;
	}else {
		echo '<div>Módulo $_POST no encontrado</div>'.json_encode($_POST);
	}
	ob_end_flush();
?>