Create a Payment Session

The request body that creates a payment session, field by field, and the URL it returns.

This is the main endpoint for initiating a Hosted Checkout payment. It creates a new payment session and returns a secure URL where your customer completes their payment.

POST https://api-stage.tonder.io/checkout/v1/sessions   # Sandbox
POST https://api.tonder.io/checkout/v1/sessions          # Production

How it works

  1. Your server calls this endpoint with payment details (amount, items, customer info).
  2. Tonder creates a secure session and returns a checkout URL.
  3. You redirect your customer to this URL.
  4. The customer completes the payment on Tonder's hosted page.
  5. The customer is redirected back to your success_url or return_url.

Include the x-idempotency-key header to prevent duplicate sessions (see Idempotency) and the ui_config object to customize the page (see Customize the checkout).

The payment_method_types field defaults to ["card"]. Accepted values: card, mercadopago, oxxopay, spei, safetypayCash, safetypayTransfer, neosurf, saved_cards.

Saved cards

Include saved_cards in payment_method_types and the checkout shows the customer's previously saved cards alongside the new card form. Listing, selecting and deleting them is handled for you — there is no extra endpoint to call.

This is the Hosted Checkout path. If you render your own form with the Web SDK, saved cards work differently — see Saved cards (secure_token).

The save-card checkbox

Set payment_method_config.saved_cards.show_save_card_checkbox to true to put a Guardar tarjeta para futuros pagos checkbox on the new card form, so the customer can opt in to saving their card.

FieldTypeDescription
show_save_card_checkboxbooleanShows a "Guardar tarjeta para futuros pagos" checkbox on the new card form, letting the customer opt in to saving their card.
curl -X POST 'https://api-stage.tonder.io/checkout/v1/sessions' \
  -H 'Authorization: Token YOUR_TEST_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
    "customer": { "first_name": "Maria", "last_name": "Garcia", "email": "maria@example.com" },
    "amount_total": 150.00,
    "currency": "MXN",
    "line_items": [
      { "name": "Premium Plan", "quantity": 1, "unit_price": 150.00 }
    ],
    "payment_method_types": ["card", "saved_cards"],
    "payment_method_config": {
      "saved_cards": { "show_save_card_checkbox": true }
    },
    "external_id": "ORD-001",
    "return_url": "https://your-store.com/checkout/complete"
  }'
curl -X POST 'https://api.tonder.io/checkout/v1/sessions' \
  -H 'Authorization: Token YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
    "customer": { "first_name": "Maria", "last_name": "Garcia", "email": "maria@example.com" },
    "amount_total": 150.00,
    "currency": "MXN",
    "line_items": [
      { "name": "Premium Plan", "quantity": 1, "unit_price": 150.00 }
    ],
    "payment_method_types": ["card", "saved_cards"],
    "payment_method_config": {
      "saved_cards": { "show_save_card_checkbox": true }
    },
    "external_id": "ORD-001",
    "return_url": "https://your-store.com/checkout/complete"
  }'

Card-on-File

Card-on-File (COF) saves cards automatically and lets the customer pay again without re-entering their CVV. It runs on Tonder's subscription and tokenization infrastructure.

When your business has an active Tonder connection with active_subscription, the checkout:

  1. Runs 3DS verification as the card is saved.
  2. Creates a subscription for that card.
  3. Accepts CVV-free payments with it on return visits.

There is nothing to configure. If Card-on-File is enabled for your account, the checkout does all of this on its own. It is the same subscription the SDK surfaces as subscription_id — see the Web SDK reference.

Sending show_save_card_checkbox: true while Card-on-File is active will not show the checkbox. That is expected: Card-on-File takes precedence and cards are saved automatically either way.

API reference

POST
/checkout/v1/sessions

Authorization

Authorization
Authorization<token>

Tu API key con prefijo Token , p. ej. Token <API_KEY>

In: header

Request Body

application/json

TypeScript Definitions

Use the request body type in TypeScript.

Response Body

application/json

curl -X POST "https://example.com/checkout/v1/sessions" \  -H "Content-Type: application/json" \  -d '{    "customer": {      "first_name": "John",      "last_name": "Doe",      "email": "john.doe@example.com"    },    "amount_total": 350,    "currency": "MXN",    "line_items": [      {        "name": "Product 1",        "quantity": 1,        "unit_price": 150,        "product_id": "prod-001"      },      {        "name": "Product 2",        "quantity": 2,        "unit_price": 100,        "product_id": "prod-002"      }    ],    "return_url": "https://my-store.com/checkout/complete",    "external_id": "ORD-12345"  }'
{
  "id": "cs_97_41521_d11ba771527b4056c7f85786cfbb980bc105efaf42af113d",
  "url": "https://stage-payflow.tonder.io/checkout/cs_97_41521_d11ba771527b4056c7f85786cfbb980bc105efaf42af113d",
  "status": "pending",
  "payment_id": 41521,
  "amount_total": 350,
  "currency": "MXN",
  "expires_at": 1751564943,
  "external_id": "ORD-12345",
  "session_type": "payment",
  "checkout_type": "hosted",
  "return_url": "https://my-store.com/checkout/complete",
  "metadata": {},
  "payment_method_types": [
    "card"
  ],
  "ui_config": {},
  "ui_config_version": "V1",
  "created_at": 1751478543567,
  "modified_at": 1751478543567,
  "customer": {
    "first_name": "John",
    "last_name": "Doe",
    "email": "john.doe@example.com"
  },
  "line_items": [
    {
      "name": "Product 1",
      "quantity": 1,
      "unit_price": 150,
      "product_id": "prod-001"
    }
  ],
  "transaction_status": "Pending",
  "provider": "tonder"
}

The session starts in pending and transitions to a final state. See the full values in the Reference.

Next steps

Was this page helpful?

On this page