# Actualizaciones del estado del pago Controla y verifica el estado del pago para poder responder tanto a los pagos realizados correctamente como a los fallidos. Los *PaymentIntents* (The Payment Intents API tracks the lifecycle of a customer checkout flow and triggers additional authentication steps when required by regulatory mandates, custom Radar fraud rules, or redirect-based payment methods) se actualizan en respuesta a acciones ejecutadas por el cliente o el método de pago. Tu integración puede inspeccionar el PaymentIntent para determinar el estado del proceso de pago y que puedas tomar medidas comerciales o responder a estados que requieran mayor intervención. También puedes usar el Dashboard de Stripe para configurar tu cuenta para que te envíe un correo electrónico sobre el estado de un pago, como los pagos realizados correctamente. Cambia tus [notificaciones por correo electrónico](https://docs.stripe.com/get-started/account/teams.md#email-notifications) en tu [configuración de usuario](https://dashboard.stripe.com/settings/user). ## Estatus de pago y estatus de los PaymentIntents La página [Payments](https://dashboard.stripe.com/payments) en el Dashboard muestra un estado de pago para cada operación, que puedes utilizar para filtrar la lista. Este estado resume el pago, pero no incluye los detalles adicionales proporcionados por el [status](https://docs.stripe.com/api/payment_intents/object.md#payment_intent_object-status) del PaymentIntent. El `status` de un PaymentIntent realiza un seguimiento del estado de un pago e indica cuándo un pago requiere más procesamiento o acciones por parte del cliente. Un pago que utiliza un PaymentIntent puede requerir un método de pago, confirmación u otra acción para realizarse correctamente. En el Dashboard, estos estados se asignan a **Incompleto**. Para entender el estado incompleto de un pago, haz clic en el pago y usa [Workbench Inspector](https://docs.stripe.com/workbench/overview.md#inspector) para ver los detalles del PaymentIntent en formato JSON. Busca `status` para ver el valor exacto. En la siguiente tabla se asigna cada `status` de PaymentIntent a los estados de pago en el Dashboard. Los casos extremos, como los intentos caducados y los códigos de pago rechazado específicos, pueden afectar a esta asignación. Usa la API o Workbench Inspector para obtener el estado autoritativo. | `Estado` del PaymentIntent | Estado del pago | Descripción | | --- | --- | --- | | `requires_payment_method` | **Incompleto** | Normalmente ocurre si no hay un [latest_charge](https://docs.stripe.com/api/payment_intents/object.md#payment_intent_object-latest_charge) o si el intent no ha avanzado más allá del cobro. Según el método de pago, los importes y los errores, el estatus de pago también puede ser **Pagado parcialmente**, **Esperando fondos** o **Fallido**. | | `requires_confirmation` | **Incompleto** | Ocurre después de que tu cliente proporciona la información de pago y está listo para confirmar. La mayoría de las integraciones omiten este estado porque envían la información del método de pago cuando se confirma el pago. | | `requires_action` | **Incompleto** | Ocurre cuando el pago requiere acciones adicionales, como autenticar con [3D Secure](https://docs.stripe.com/payments/3d-secure.md). El estado de pago en el Dashboard también puede ser **Pagado parcialmente**, **Esperando fondos** o **Fallido** en determinadas condiciones de autenticación o error. | | `processing` | **Pendiente** | Ocurre cuando las acciones requeridas se han completado y el pago utiliza un *método de pago asíncrono* (Asynchronous payment methods can take up to several days to confirm whether the payment has been successful. During this time, the payment can't be guaranteed), como los adeudos bancarios. Estos métodos de pago pueden tardar unos días en procesarse. | | `requires_capture` | **No capturado** o **Captura parcial** | Ocurre si tu flujo utiliza la [captura separada](https://docs.stripe.com/payments/place-a-hold-on-a-payment-method.md). Si se recibe algún importe para el intent, el estatus es **Captura parcial**. Si no se recibe ningún importe, el estatus es **No capturado**. | | `succeeded` | **Completado** | Un PaymentIntent con un estatus `succeeded` significa que el flujo de pago correspondiente está completo. Los fondos están en tu cuenta y puedes preparar el pedido. Si el intento de pago falla (por ejemplo, debido a un pago rechazado), el estatus del PaymentIntent vuelve a ser `requires_payment_method` para que se pueda volver a intentar el pago. Los reembolsos, disputas y resultados posteriores se reflejan en el Cargo. Estos pueden cambiar lo que ves en el Dashboard, aunque el PaymentIntent siga siendo `succeeded`. | | `cancelado` | **Cancelado** | Ocurre cuando el pago se cancela. Si el intent se canceló como parte de un flujo de factura fallido y el último cargo falló, el estatus podría mostrarse como **Fallido**. | ## Gestiona las siguientes acciones Algunos métodos de pago requieren pasos adicionales, como la autenticación, para completar el proceso de pago. Stripe.js los gestiona de manera automática al confirmar el PaymentIntent, pero si tienes una integración avanzada, puedes gestionarlos manualmente. La propiedad [next_action](https://docs.stripe.com/api/payment_intents/object.md#payment_intent_object-next_action) del PaymentIntent expone el siguiente paso que tu integración debe gestionar para completar el pago. Las siguientes acciones disponibles varían según el método de pago. Para ver la lista completa, consulta la [referencia de la API](https://docs.stripe.com/api.md#payment_intent_object-next_action-type). Aprende a [gestionar las siguientes acciones requeridas de un método de pago](https://docs.stripe.com/payments/payment-methods/overview.md). ## Comprueba el estado del PaymentIntent del lado del cliente Cuando el cliente completa un pago con la función [confirmPayment](https://docs.stripe.com/js/payment_intents/confirm_payment), puedes inspeccionar el PaymentIntent devuelto para determinar su estado actual: ```javascript (async () => { const {paymentIntent, error} = await stripe.confirmPayment({ elements, confirmParams: { return_url: 'https://example.com/order/complete', }, redirect: 'if_required', }); if (error) { // Handle error here } else if (paymentIntent && paymentIntent.status === 'succeeded') { // Handle successful payment here } })(); ``` A continuación, indicamos algunos de los posibles resultados al utilizar la función `confirmPayment`: | **Evento** | **Qué ha ocurrido** | **Integración prevista** | | --- | --- | --- | | Resuelve con un PaymentIntent | El cliente completó el pago en la página de proceso de compra | Informa al cliente de que el pago se efectuó correctamente | | Resuelve con un error | El pago del cliente no pudo completarse en la página de proceso de compra | Muestra un mensaje de error y solicita al cliente que vuelva a intentar el pago | La promesa devuelta por `confirmPayment` se resuelve cuando el proceso de pago se completa o falla al dar error. Cuando se completa correctamente y devuelve un PaymentIntent, el estado siempre será `succeeded` (o `requires_capture` si se [captura el importe más tarde](https://docs.stripe.com/payments/place-a-hold-on-a-payment-method.md)). Cuando el pago requiere un paso adicional, como la autenticación, la promesa no se resuelve hasta que el paso se completa o se agota el tiempo de espera. ## Comprueba el estado del PaymentIntent del lado del cliente sin usar confirmPayment Para comprobar el estado de un PaymentIntent sin usar la función `confirmPayment`, recupéralo de forma independiente usando la función [retrievePaymentIntent](https://docs.stripe.com/js/payment_intents/retrieve_payment_intent) y pasando el *secreto del cliente* (The client secret is a unique key returned from Stripe as part of a PaymentIntent. This key lets the client access important fields from the PaymentIntent (status, amount, currency) while hiding sensitive ones (metadata, customer)). ```javascript (async () => { const {paymentIntent} = await stripe.retrievePaymentIntent(clientSecret); if (paymentIntent && paymentIntent.status === 'succeeded') { // Handle successful payment here } else { // Handle unsuccessful, processing, or canceled payments and API errors here } })(); ``` Estos son algunos de los [posibles estados](https://docs.stripe.com/api/payment_intents/object.md#payment_intent_object-status) del PaymentIntent después de una confirmación: | **Qué ha ocurrido** | **Estado previsto del PaymentIntent** | | --- | --- | | El cliente completó el pago en la página de proceso de compra | `succeeded` | | El cliente no completó el proceso de compra | `requires_action` | | El pago del cliente no pudo completarse en la página de proceso de compra | `requires_payment_method` | [Obtén más información sobre los estados de PaymentIntent](https://docs.stripe.com/payments/paymentintents/lifecycle.md). ## Supervisa un PaymentIntent con webhooks Stripe puede enviar eventos de *webhooks* (A webhook is a real-time push notification sent to your application as a JSON payload through HTTPS requests) a tu servidor para notificarte los cambios que se produzcan en el estado de un PaymentIntent. Esto resulta útil, por ejemplo, para determinar cuándo entregar bienes y servicios. No intentes gestionar *la ejecución de pedidos* (Fulfillment is the process of providing the goods or services purchased by a customer, typically after payment is collected) del lado del cliente porque el cliente puede salir de la página después de efectuar el pago, pero antes de que se inicie el proceso de ejecución de pedidos. En lugar de iniciarlo del lado del cliente, utiliza webhooks para supervisar el evento `payment_intent.succeeded` y gestionar la ejecución del pedido de forma asincrónica. > Aunque es posible usar el sondeo en lugar de webhooks para supervisar los cambios provocados por las operaciones asincrónicas (es decir, recuperar repetidamente un PaymentIntent para que puedas comprobar su estado), esto es mucho menos fiable y puede causar problemas de limitación de velocidad. Stripe aplica [límites de velocidad](https://docs.stripe.com/testing.md#rate-limits) en las solicitudes de API, así que ten cuidado si usas el sondeo. Para gestionar un evento de webhook, crea una ruta en tu servidor y configura el punto de conexión de webhook correspondiente [en el Dashboard](https://dashboard.stripe.com/account/webhooks). Stripe envía el evento `payment_intent.succeeded` cuando el pago se realiza correctamente y el evento `payment_intent.payment_failed` cuando el pago falla. La carga del webhook incluye el objeto PaymentIntent. El siguiente ejemplo muestra cómo gestionar ambos eventos: #### Ruby ```ruby require 'sinatra' require 'stripe' post '/webhook' do payload = request.body.read sig_header = request.env['HTTP_STRIPE_SIGNATURE'] event = nil begin event = Stripe::Webhook.construct_event( payload, sig_header, endpoint_secret ) rescue JSON::ParserError => e # Invalid payload status 400 return rescue Stripe::SignatureVerificationError => e # Invalid signature status 400 return end case event['type'] when 'payment_intent.succeeded' intent = event['data']['object'] puts "Succeeded:", intent['id'] # Fulfill the customer's purchase when 'payment_intent.payment_failed' intent = event['data']['object'] error_message = intent['last_payment_error'] && intent['last_payment_error']['message'] puts "Failed:", intent['id'], error_message # Notify the customer that payment failed end status 200 end ``` Cuando el pago falla, puedes encontrar más detalles si inspeccionas la propiedad `last_payment_error` del PaymentIntent. Asimismo, puedes notificar al cliente que el pago no se completó y animarlo a intentarlo de nuevo con otro método de pago. Reutiliza el mismo PaymentIntent para continuar el seguimiento de la compra del cliente. ### Cómo gestionar eventos de webhook específicos La siguiente lista describe cómo gestionar eventos de webhook: | Evento | Descripción | Siguientes pasos | | --- | --- | --- | | `processing` | El pago del cliente se envió a Stripe correctamente. Solo se aplica a métodos de pago con [notificación de confirmación diferida](https://docs.stripe.com/payments/payment-methods.md#payment-notification). | Espera hasta saber si el pago iniciado se hizo efectivo o no. | | `succeeded` | El pago del cliente se ha realizado correctamente. | Completa el pedido de los productos o servicios comprados. | | `amount_capturable_updated` | Se autorizó el pago del cliente y está listo para la captura. | Captura los fondos disponibles para el pago. | | `payment_failed` | La red de tarjeta rechazó el pago del cliente o este caducó. | Contacta con el cliente mediante un correo electrónico o una notificación emergente, y solicítale que proporcione otro método de pago. | Para probar los webhooks localmente, puedes utilizar [la CLI de Stripe](https://docs.stripe.com/stripe-cli.md). Después de instalarla, puedes reenviar los eventos a tu servidor: ```bash stripe listen --forward-to localhost:4242/webhook Ready! Your webhook signing secret is '{{WEBHOOK_SIGNING_SECRET}}' (^C to quit) ``` Obtén más información sobre [cómo configurar webhooks](https://docs.stripe.com/webhooks.md). ## Cómo identificar cargos en un PaymentIntent Cuando intentas cobrar un pago a un cliente, el PaymentIntent crea un [cargo](https://docs.stripe.com/api/charges.md). Para obtener el ID del cargo más reciente, inspecciona la propiedad [latest_charge](https://docs.stripe.com/api/payment_intents/object.md#payment_intent_object-latest_charge) del PaymentIntent: #### Ruby ```ruby # Don't put any keys in code. See https://docs.stripe.com/keys-best-practices. # Find your keys at https://dashboard.stripe.com/apikeys. client = Stripe::StripeClient.new('<>') intent = client.v1.payment_intents.retrieve('{{PAYMENT_INTENT_ID}}') latest_charge = intent.latest_charge ``` Para ver todos los cargos asociados con un PaymentIntent, incluidos los cargos fallidos, [haz una lista de todos los cargos](https://docs.stripe.com/api/charges/list.md#list_charges-payment_intent) y especifica el parámetro `payment_intent​`. ```curl curl -G https://api.stripe.com/v1/charges \ -u "<>:" \ -d "payment_intent={{PAYMENTINTENT_ID}}" ```