Card - Integrate payment methods - Mercado Pago Developers

Integrate Checkout API payment for cards

Integrating Mercado Pago's Checkout API for cards allows you to offer a complete payment option within the site. The entire experience takes place in your store, so customers avoid exiting your site while making a purchase.

Important
Your integration with Mercado Pago's transparent API may be eligible for . This category of PCI requires fewer requirements from the seller, which speeds up the certification process. To be eligible for this category, its integration must be done using card fields in Iframe format.

Fields uses HTML components allows PCI data (cardNumber, securityCode, and expirationDate) to be inaccessible to third parties and processed by Mercado Pago servers, increasing security for buyers, vendors, and acquirers.

Fields

There are currently two ways to implement this solution. The first is through the use of core methods, where the integrator is responsible for the entire payment flow, allowing greater flexibility for fully customized experiences. The second one uses cardForm, a component created by us that facilitates the integration, carrying out some steps of the process automatically.

Use our sample projects for a complete integration. You can adapt them according to your needs.

How does it work?

API-integration-flowchart

If you want to make a customized payment flow, we share all the .

With our Mercado Pago Checkout API, you should take into account two aspects: data capture and payment confirmation submission.

  1. First, you need a frontend to collect card data and generate a security token with the information required to create a payment.
  2. Then, you need a backend that takes the generated token and payment data, such as amount and item, to confirm and make a payment.

Both for frontend and backend, we recommend our libraries to collect user sensitive data securely.

Note
For more information, check .

Card data capture

Client-Side

To create a payment, you should capture card data through the buyer's browser. For security reasons, never store data in your servers.

To capture card data, follow these steps:

  1. Include and configure MercadoPago.js library
  2. Add payment form
  3. Integrate the form with MercadoPago.js library

1. Include and configure MercadoPago.js library

Use our official library to access Mercado Pago API from your frontend to collect data securely and to configure your public key like this:

html

<body>
  <!-- Add step #2 -->
  <script src="https://sdk.mercadopago.com/js/v2"></script>
  <script>
      const mp = new MercadoPago('YOUR_PUBLIC_KEY');
      // Add step #3
  </script>
</body>

Card information will be turned into a token so that you can send data to your servers securely.

If you still don't have an account to check your credentials, sign in.

The card information will be converted into a token so you can send the data to your servers in a secure way.

2. Add payment form

Before capturing the card data, provide a form to load all the information.

With MercadoPago.js library CardForm functionality you can get and validate all the data needed to identify the type and name of payment method, issuing bank, number of installments and more.

CardForm provides secure implementation and correct token of card data.

For the PCI fields (Card Number, Expiration Date and Security Code) you must create divs that will serve as containers for the iFrames.

Use the following form and add the styles of your choice.

html

<!-- Step #2 -->
<style>
  #form-checkout {
    display: flex;
    flex-direction: column;
    max-width: 600px;
  }

  .container {
    height: 18px;
    display: inline-block;
    border: 1px solid rgb(118, 118, 118);
    border-radius: 2px;
    padding: 1px 2px;
  }
</style>
<form id="form-checkout">
   <div id="form-checkout__cardNumber-container" class="container"></div>
   <div id="form-checkout__expirationDate-container" class="container"></div>
   <input type="text" name="cardholderName" id="form-checkout__cardholderName"/>
   <input type="email" name="cardholderEmail" id="form-checkout__cardholderEmail"/>
   <div id="form-checkout__securityCode-container" class="container"></div>
   <select name="issuer" id="form-checkout__issuer"></select>
   <select name="identificationType" id="form-checkout__identificationType"></select>
   <input type="text" name="identificationNumber" id="form-checkout__identificationNumber"/>
   <select name="installments" id="form-checkout__installments"></select>
   <button type="submit" id="form-checkout__submit">Pay</button>
   <progress value="0" class="progress-bar">Loading...</progress>
 </form>
Technical reference
Find information about the different attributes in the .

3. Integrate the form with MercadoPago.js library

Now, to initialize the CardForm, relate each form field ID with the relevant attributes. The library will be responsible for filling out, getting and validating all the data needed for payment confirmation.

For the IFrame to be rendered, it is necessary to pass the iframe option with true value in the parameter object received by the cardForm. It is also possible to pass the style to the elements.

javascript


// Step #3
const cardForm = mp.cardForm({
   amount: '100.5',
   iframe: true,
   form: {
     id: 'form-checkout',
     cardholderName: {
       id: 'form-checkout__cardholderName',
       placeholder: "Card Holder",
     },
     cardholderEmail: {
       id: 'form-checkout__cardholderEmail',
       placeholder: 'E-mail'
     },
     cardNumber: {
       id: 'form-checkout__cardNumber-container',
       placeholder: 'Card Number',
     },
     securityCode: {
       id: 'form-checkout__securityCode-container',
       placeholder: 'CVV'
     },
     installments: {
       id: 'form-checkout__installments',
       placeholder: 'Installments'
     },
     expirationDate: {
       id: 'form-checkout__expirationDate-container',
       placeholder: 'Expiration Date (MM/YYYY)',
     },
     identificationType: {
       id: 'form-checkout__identificationType',
       placeholder: 'Document type'
     },
     identificationNumber: {
       id: 'form-checkout__identificationNumber',
       placeholder: 'Document value'
     },
     issuer: {
       id: 'form-checkout__issuer',
       placeholder: 'Issuer'
     }
   },
   callbacks: {
     onFormMounted: function (error) {
       if (error) return console.log('Callback para tratar o erro: montando o cardForm ', error)
     },
     onSubmit: function (event) {
       event.preventDefault();
 
       const {
         paymentMethodId: payment_method_id,
         issuerId: issuer_id,
         cardholderEmail: email,
         amount,
         token,
         installments,
         identificationNumber,
         identificationType
       } = cardForm.getCardFormData();
 
        fetch('/process_payment', {
          method: 'POST',
          headers: {
            'Content-Type': 'application/json'
          },
          body: JSON.stringify({
            token,
            issuer_id,
            payment_method_id,
            transaction_amount: Number(amount),
            installments: Number(installments),
            description: 'product description',
            payer: {
              email,
              identification: {
                type: identificationType,
                number: identificationNumber
             }
           }
         })
       })
     },
     onFetching: function (resource) {
       console.log('fetching... ', resource)
       const progressBar = document.querySelector('.progress-bar')
       progressBar.removeAttribute('value')
 
       return () => {
         progressBar.setAttribute('value', '0')
       }
     }
   }
 });

The callbacks option accepts different functions that are activated in different flow moments.

Technical reference
Learn more information about callbacks in the .

When submitting the form, we generate a token as a secure representation of the card data. You can access this token using the getCardFormData function, as we showed in the previous example in the onSubmit callback. We will also store the token in a hidden input within your form which we will name MPHiddenInputToken.

Important
Remember that the token is valid for 7 days and can be used only once.

Payment submission to Mercado Pago

Server-Side

To continue with the Mercado Pago payment process, your backend should know how to receive form information with the generated token and the filled out data.

In the above example, after the submit action, your backend should make available a /process_payment endpoint, to receive all the data.

Once the request –with all the collected information– is in your backend, it should be submitted to Mercado Pago through our APIs. The minimum mandatory fields to submit are: token, transaction_amount, installments, payment_method_id and payer.email.

For this to work, you should configure your private key. Also, to interact with our APIs, you should use Mercado Pago official SDK.

Find the payment status in the status field.

          
<?php
   require_once 'vendor/autoload.php';
 
   MercadoPago\SDK::setAccessToken("YOUR_ACCESS_TOKEN");
 
   $payment = new MercadoPago\Payment();
   $payment->transaction_amount = (float)$_POST['transactionAmount'];
   $payment->token = $_POST['token'];
   $payment->description = $_POST['description'];
   $payment->installments = (int)$_POST['installments'];
   $payment->payment_method_id = $_POST['paymentMethodId'];
   $payment->issuer_id = (int)$_POST['issuer'];
 
   $payer = new MercadoPago\Payer();
   $payer->email = $_POST['email'];
   $payer->identification = array(
       "type" => $_POST['identificationType'],
       "number" => $_POST['identificationNumber']
   );
   $payment->payer = $payer;
 
   $payment->save();
 
   $response = array(
       'status' => $payment->status,
       'status_detail' => $payment->status_detail,
       'id' => $payment->id
   );
   echo json_encode($response);
 
?>

        

Find the payment status in the status field.

          
 
var mercadopago = require('mercadopago');
mercadopago.configurations.setAccessToken("YOUR_ACCESS_TOKEN");
 
mercadopago.payment.save(req.body)
  .then(function(response) {
    const { status, status_detail, id } = response.body;
    res.status(response.status).json({ status, status_detail, id });
  })
  .catch(function(error) {
    console.error(error);
  });

        

Find the payment status in the status field.

          

PaymentClient client = new PaymentClient();

PaymentCreateRequest paymentCreateRequest =
   PaymentCreateRequest.builder()
       .transactionAmount(request.getTransactionAmount())
       .token(request.getToken())
       .description(request.getDescription())
       .installments(request.getInstallments())
       .paymentMethodId(request.getPaymentMethodId())
       .payer(
           PaymentPayerRequest.builder()
               .email(request.getPayer().getEmail())
               .firstName(request.getPayer().getFirstName())
               .identification(
                   IdentificationRequest.builder()
                       .type(request.getPayer().getIdentification().getType())
                       .number(request.getPayer().getIdentification().getNumber())
                       .build())
               .build())
       .build();

client.create(paymentCreateRequest);


        

Find the payment status in the status field.

          
require 'mercadopago'
sdk = Mercadopago::SDK.new('YOUR_ACCESS_TOKEN')
 
payment_data = {
 transaction_amount: params[:transactionAmount].to_f,
 token: params[:token],
 description: params[:description],
 installments: params[:installments].to_i,
 payment_method_id: params[:paymentMethodId],
 payer: {
   email: params[:email],
   identification: {
     type: params[:identificationType],
     number: params[:identificationNumber]
   }
 }
}
 
payment_response = sdk.payment.create(payment_data)
payment = payment_response[:response]
 
puts payment
 

        

Find the payment status in the status field.

          
using System;
using MercadoPago.Client.Common;
using MercadoPago.Client.Payment;
using MercadoPago.Config;
using MercadoPago.Resource.Payment;
 
MercadoPagoConfig.AccessToken = "YOUR_ACCESS_TOKEN";
 
var paymentRequest = new PaymentCreateRequest
{
   TransactionAmount = decimal.Parse(Request["transactionAmount"]),
   Token = Request["token"],
   Description = Request["description"],
   Installments = int.Parse(Request["installments"]),
   PaymentMethodId = Request["paymentMethodId"],
   Payer = new PaymentPayerRequest
   {
       Email = Request["email"],
       Identification = new IdentificationRequest
       {
           Type = Request["identificationType"],
           Number = Request["identificationNumber"],
       },
   },
};
 
var client = new PaymentClient();
Payment payment = await client.CreateAsync(paymentRequest);
 
Console.WriteLine(payment.Status);
 

        

Find the payment status in the status field.

          
import mercadopago
sdk = mercadopago.SDK("ACCESS_TOKEN")
 
payment_data = {
   "transaction_amount": float(request.POST.get("transaction_amount")),
   "token": request.POST.get("token"),
   "description": request.POST.get("description"),
   "installments": int(request.POST.get("installments")),
   "payment_method_id": request.POST.get("payment_method_id"),
   "payer": {
       "email": request.POST.get("email"),
       "identification": {
           "type": request.POST.get("type"), 
           "number": request.POST.get("number")
       }
   }
}
 
payment_response = sdk.payment().create(payment_data)
payment = payment_response["response"]
 
print(payment)

        

Find the payment status in the status field.

          
 
curl -X POST \
   -H 'accept: application/json' \
   -H 'content-type: application/json' \
   -H 'Authorization: Bearer YOUR_ACCESS_TOKEN' \
   'https://api.mercadopago.com/v1/payments' \
   -d '{
         "transaction_amount": 100,
         "token": "ff8080814c11e237014c1ff593b57b4d",
         "description": "Blue shirt",
         "installments": 1,
         "payment_method_id": "visa",
         "issuer_id": 310,
         "payer": {
           "email": "test@test.com"
         }
   }'
 

        

Response

json

{
   "status": "approved",
   "status_detail": "accredited",
   "id": 3055677,
   "date_approved": "2019-02-23T00:01:10.000-04:00",
   "payer": {
       ...
   },
   "payment_method_id": "visa",
   "payment_type_id": "credit_card",
   "refunds": [],
   ...
}
Check to learn about all the available fields for full payments.

Response Handling

Possible payment statuses are:

payment-status

For improved payment approval, you need to correctly inform results to your customers when making or creating a payment.

This will prevent rejections and chargebacks in case of already approved transactions. For example, this allows you to correct data upload mistakes or change payment methods.

We recommend using response handling and the suggested communication in each case.

Note
Avoid rejected payments with our recommendations to .

Receive payment notifications

Finally, you always need to be notified of new payments and status updates. For example, if they were approved, rejected, or are pending.

Configure webhook notifications or IPN notifications.

Sample projects

Checkout API
Use our to download instantly.