status, [PaymentStatus::PENDING, PaymentStatus::PROCESSING])) {
return;
}
try {
// Obtener el booking para acceder al restaurant_id
$booking = $this->booking;
if (!$booking) {
return;
}
// Crear instancia del gateway Stripe
if (!class_exists('\Alexr\Payments\GatewayStripe')) {
return;
}
$gateway = new \Alexr\Payments\GatewayStripe($booking->restaurant_id);
// Obtener el payment_intent_id
$payment_intent_id = $this->stripe_payment_intent_id;
if (!$payment_intent_id) {
error_log("Stripe payment check: No payment intent ID found for payment {$this->id}");
return;
}
// Verificar si es un SetupIntent (captura de tarjeta) o PaymentIntent
$isSetupIntent = (substr($payment_intent_id, 0, 5) === 'seti_');
// Consultar el estado actual en Stripe
if ($isSetupIntent) {
// Para SetupIntent (captura de tarjeta)
$client = $gateway->getClient();
$intent = $client->setupIntents->retrieve($payment_intent_id);
$stripe_status = $intent->status;
} else {
// Para PaymentIntent (pagos normales)
$intent = $gateway->getPaymentIntent($payment_intent_id);
if (!$intent) {
error_log("Stripe payment check: Could not retrieve PaymentIntent {$payment_intent_id}");
return;
}
$stripe_status = $intent->status;
}
$previous_status = $this->status;
$payment_updated = false;
$new_status_text = '';
// Mapear el estado de Stripe a nuestro sistema
switch ($stripe_status) {
case 'succeeded':
if ($this->status !== PaymentStatus::SUCCEEDED) {
error_log("Stripe payment status check: Payment {$this->id} is now SUCCEEDED, updating status");
$this->status = PaymentStatus::SUCCEEDED;
$this->stripe_payment_status = $stripe_status;
// Actualizar el booking
$booking->status = $booking->paymentStatus;
$booking->save();
// Enviar notificaciones
$booking->sendBookingEmail();
$booking->sendSmsNotification();
$booking->sendWhatsappNotification();
$payment_updated = true;
$new_status_text = 'SUCCEEDED';
}
break;
case 'requires_capture':
if ($this->status !== PaymentStatus::PENDING_CAPTURE) {
error_log("Stripe payment status check: Payment {$this->id} requires capture, updating status");
$this->status = PaymentStatus::PENDING_CAPTURE;
$this->stripe_payment_status = $stripe_status;
$payment_updated = true;
$new_status_text = 'REQUIRES_CAPTURE';
}
break;
case 'processing':
if ($this->status !== PaymentStatus::PROCESSING) {
error_log("Stripe payment status check: Payment {$this->id} is processing, updating status");
$this->status = PaymentStatus::PROCESSING;
$this->stripe_payment_status = $stripe_status;
$payment_updated = true;
$new_status_text = 'PROCESSING';
}
break;
case 'canceled':
case 'cancelled':
if ($this->status !== PaymentStatus::CANCELLED) {
error_log("Stripe payment status check: Payment {$this->id} is canceled, updating status");
$this->status = PaymentStatus::CANCELLED;
$this->stripe_payment_status = $stripe_status;
$payment_updated = true;
$new_status_text = 'CANCELLED';
}
break;
case 'requires_payment_method':
case 'requires_confirmation':
case 'requires_action':
// Mantener como PENDING pero actualizar stripe_payment_status
if ($this->stripe_payment_status !== $stripe_status) {
$this->stripe_payment_status = $stripe_status;
$payment_updated = true;
$new_status_text = strtoupper($stripe_status);
}
break;
}
if ($payment_updated) {
// Actualizar settings con la información actualizada
$settings = $this->settings ?? [];
// Actualizar los datos del payment intent
$settings['payment_intent'] = json_decode(json_encode($intent), true);
// Agregar información de la verificación
$settings['status_check'] = [
'checked_at' => date('Y-m-d H:i:s'),
'previous_status' => $previous_status,
'new_status' => $this->status,
'stripe_status' => $stripe_status,
'intent_type' => $isSetupIntent ? 'setup_intent' : 'payment_intent',
'source' => 'manual_check'
];
$this->settings = $settings;
$this->save();
error_log("Stripe payment successfully updated: booking {$booking->uuid}, status: {$new_status_text}");
}
} catch (\Exception $e) {
error_log('Stripe payment status check error: ' . $e->getMessage());
}
}
/**
* Obtiene los datos de Stripe formateados para mostrar
*/
public function getStripeDataFormattedAttribute()
{
// Verificar estado del pago antes de mostrar los datos
$this->checkStripePaymentStatus();
$settings = $this->settings;
if (empty($settings)) {
return '
";
// Mostrar mensaje si se actualizó el estado
if (isset($settings['status_check'])) {
$statusCheck = $settings['status_check'];
$message .= "
";
$message .= "Status Updated: Payment status was automatically updated on {$statusCheck['checked_at']} from {$statusCheck['previous_status']} to {$statusCheck['new_status']} (Stripe: {$statusCheck['stripe_status']})";
$message .= "
";
}
// Información principal del Payment Intent
if (isset($settings['payment_intent'])) {
$paymentIntent = $settings['payment_intent'];
$message .= "
Payment Intent Information
";
$message .= "
Payment Intent ID: {$paymentIntent['id']}
";
$message .= "
Status: " . strtoupper($paymentIntent['status']) . "
";
$message .= "
Amount: " . number_format($paymentIntent['amount'] / 100, 2) . " " . strtoupper($paymentIntent['currency']) . "
";
if (isset($paymentIntent['amount_received']) && $paymentIntent['amount_received'] > 0) {
$message .= "
Amount Received: " . number_format($paymentIntent['amount_received'] / 100, 2) . " " . strtoupper($paymentIntent['currency']) . "
";
}
if (isset($paymentIntent['description']) && $paymentIntent['description']) {
$message .= "
Description: {$paymentIntent['description']}
";
}
$message .= "
Created: " . date('Y-m-d H:i:s', $paymentIntent['created']) . "
";
if (isset($paymentIntent['confirmation_method'])) {
$message .= "
Confirmation Method: " . strtoupper($paymentIntent['confirmation_method']) . "
";
}
if (isset($paymentIntent['capture_method'])) {
$message .= "
Capture Method: " . strtoupper($paymentIntent['capture_method']) . "
";
}
// Información del cliente si existe
if (isset($paymentIntent['customer']) && $paymentIntent['customer']) {
$message .= "
Customer ID: {$paymentIntent['customer']}
";
}
// Payment Method utilizado
if (isset($paymentIntent['payment_method']) && $paymentIntent['payment_method']) {
$message .= "
Payment Method ID: {$paymentIntent['payment_method']}
";
}
// Información del último charge si existe
if (isset($paymentIntent['latest_charge']) && $paymentIntent['latest_charge']) {
$message .= "
Latest Charge ID: {$paymentIntent['latest_charge']}
";
}
// Fees de Stripe si existen
if (isset($paymentIntent['charges']['data'][0]['balance_transaction'])) {
$balanceTransaction = $paymentIntent['charges']['data'][0]['balance_transaction'];
if (isset($balanceTransaction['fee'])) {
$message .= "
Stripe Fee: " . number_format($balanceTransaction['fee'] / 100, 2) . " " . strtoupper($paymentIntent['currency']) . "
";
}
}
// Detalles del método de pago si están disponibles
if (isset($paymentIntent['charges']['data'][0]['payment_method_details'])) {
$paymentDetails = $paymentIntent['charges']['data'][0]['payment_method_details'];
if (isset($paymentDetails['card'])) {
$card = $paymentDetails['card'];
$message .= "
Card Details
";
$message .= "
Brand: " . strtoupper($card['brand']) . "
";
$message .= "
Last 4: **** **** **** {$card['last4']}
";
$message .= "
Exp: {$card['exp_month']}/{$card['exp_year']}
";
$message .= "
Country: {$card['country']}
";
if (isset($card['funding'])) {
$message .= "
Funding: " . strtoupper($card['funding']) . "
";
}
if (isset($card['network'])) {
$message .= "
Network: " . strtoupper($card['network']) . "
";
}
if (isset($card['wallet'])) {
$message .= "
Wallet: " . strtoupper($card['wallet']['type']) . "
";
}
}
}
// Información de billing si existe
if (isset($paymentIntent['charges']['data'][0]['billing_details'])) {
$billing = $paymentIntent['charges']['data'][0]['billing_details'];
if (!empty($billing['name']) || !empty($billing['email'])) {
$message .= "
Billing Details
";
if (!empty($billing['name'])) {
$message .= "
Name: {$billing['name']}
";
}
if (!empty($billing['email'])) {
$message .= "
Email: {$billing['email']}
";
}
if (!empty($billing['address']['country'])) {
$message .= "
Country: {$billing['address']['country']}
";
}
}
}
// Receipt URL si está disponible
if (isset($paymentIntent['charges']['data'][0]['receipt_url'])) {
$receiptUrl = $paymentIntent['charges']['data'][0]['receipt_url'];
$message .= "
";
}
}
// Información del Setup Intent para card capture
elseif (isset($settings['setup_intent'])) {
$setupIntent = $settings['setup_intent'];
$message .= "
Setup Intent Information (Card Capture)
";
$message .= "
Setup Intent ID: {$setupIntent['id']}
";
$message .= "
Status: " . strtoupper($setupIntent['status']) . "
";
$message .= "
Created: " . date('Y-m-d H:i:s', $setupIntent['created']) . "
";
if (isset($setupIntent['customer']) && $setupIntent['customer']) {
$message .= "
Customer ID: {$setupIntent['customer']}
";
}
if (isset($setupIntent['payment_method']) && $setupIntent['payment_method']) {
$message .= "
Payment Method ID: {$setupIntent['payment_method']}
";
}
if (isset($setupIntent['usage'])) {
$message .= "
Usage: " . strtoupper($setupIntent['usage']) . "
";
}
}
// Client Secret si existe
if (isset($settings['stripe_client_secret'])) {
$message .= "
Client Information
";
$message .= "
Client Secret: {$settings['stripe_client_secret']}
";
}
// Información adicional del payment model
$message .= "
Payment Model Information
";
$message .= "
Payment Type: " . strtoupper($this->payment_type) . "
";
$message .= "
Amount: " . number_format($this->amount / 100, 2) . " " . strtoupper($this->currency) . "
";
$message .= "
Status: " . strtoupper($this->status) . "
";
if ($this->stripe_payment_intent_id) {
$message .= "
Stripe Payment Intent ID: {$this->stripe_payment_intent_id}
";
}
if ($this->stripe_payment_status) {
$message .= "
Stripe Payment Status: " . strtoupper($this->stripe_payment_status) . "
";
}
if ($this->is_sandbox) {
$message .= "
Mode: SANDBOX/TEST
";
} else {
$message .= "
Mode: LIVE
";
}
// Enlaces útiles
if ($this->stripe_payment_intent_id) {
$dashboardUrl = $this->is_sandbox
? "https://dashboard.stripe.com/test/payments/{$this->stripe_payment_intent_id}"
: "https://dashboard.stripe.com/payments/{$this->stripe_payment_intent_id}";
$message .= "
";
}
// Mostrar datos en crudo en un área colapsable para debugging
$message .= "
Raw Data
";
$message .= "
";
$message .= "Show Raw Settings
";
$message .= "";
$message .= "
" . htmlspecialchars(json_encode($settings, JSON_PRETTY_PRINT)) . "
";
$message .= "
";
$message .= " ";
$message .= "
";
return $message;
}
}