Skip to content

Operate · Webhooks

Receive the saved card's token when a card is stored

Finrelay sends a POST with the saved payment method when a card is stored for future payments. It is signed with your merchant private key and retried 3 times.

Not on the saving payment's webhook. On the payment that saves the card, payment_method_token is null on the Transaction Processed webhook: the saved card's ID first arrives on this event. Later payments with the saved card carry it in payment_method_token.

1 Your customer Pays and agrees to save the card
2 Finrelay Stores the card · sends the event with a signed JWT
3 Your webhook endpoint Verifies the JWT and the SHA-512 digest
Finrelay Your systems

Overview

The Payment Method Tokenized Webhook is sent when Finrelay stores a card for future payments, for example after a payment where the customer chose to save the card. It carries the saved payment method's ID, which you use to charge the card later, and the transaction that saved it.

Subscribe an endpoint to it in the portal: see Configure webhooks in the portal. Its event service is separate from the transaction events, so it needs an endpoint of its own.

Supported Events

Event Value Description
tokenization-webhook:payment-method:tokenized A payment method was saved

Request Details

Detail Value
HTTP Method POST
Content-Type application/json
Authorization Header Bearer <JWT>
Timeout 15 seconds per attempt
Retries 3, with exponential backoff (about 1, 2 and 4 seconds, each varying by up to 50%). A slow endpoint can receive more; see Delivery and Retry Policy
After the last retry No further attempts
Signature Validation JWT signed using Merchant Private Key

The headers, the JWT and the retry policy are the same as for every webhook: see Security and Signature Verification and Delivery and Retry Policy.

Payload Schema

{
  "event": "tokenization-webhook:payment-method:tokenized",
  "payload": {
    "payment_method": {
      "id": "abc123def456ghi789jk",
      "type": "CARD",
      "card": {
        "brand": "VISA",
        "last_4": "1111",
        "exp_month": 12,
        "exp_year": 2028,
        "bin": "411111",
        "masked": "******1111"
      }
    },
    "transaction_id": "KlLQpgjqCmsmogHfNjuS",
    "customer": {
      "id": "CUST123456",
      "first_name": "Carey",
      "last_name": "Kuhn",
      "email": "carey.kuhn@example.com"
    },
    "merchant_id": "eyCnTugDzIMADoQLTUJF",
    "created_at": "2025-04-28T12:42:27.144339Z"
  }
}

Field Descriptions

Field Type Description
event string Always tokenization-webhook:payment-method:tokenized
payload.payment_method.id string The saved payment method's ID. Use it to charge the card later, or to delete it with DELETE /api/payment-methods/{payment_method_id}
payload.payment_method.type string The payment method type, uppercase, e.g. CARD
payload.payment_method.card.brand string or null Card brand, e.g. VISA
payload.payment_method.card.last_4 string or null Last four digits of the card number
payload.payment_method.card.exp_month integer or null Expiry month, 1–12
payload.payment_method.card.exp_year integer or null Expiry year, four digits
payload.payment_method.card.bin string or null The card's BIN
payload.payment_method.card.masked string or null The masked card number
payload.transaction_id string or null The transaction that saved the card
payload.customer.id string or null Your customer's ID, when the transaction named one
payload.customer.first_name string or null Customer first name
payload.customer.last_name string or null Customer last name
payload.customer.email string or null Customer email
payload.merchant_id string Merchant identifier
payload.created_at string (ISO-8601 datetime) When the event was created

Fields without a value are sent as null, not left out.

JSON Schema

Here is the JSON Schema for validating the Payment Method Tokenized Webhook payload (download and view):

payment-method-tokenized-payload.json

New fields can be added to the payload. The schema accepts fields it doesn't list, so don't reject a webhook because it carries a field you don't know.

Important Notes

  • Always verify the JWT signature using your merchant public key, and the SHA-512 digest of the body.
  • Duplicate deliveries are possible: key your handler on payload.payment_method.id.
  • A test sent from the portal's Test endpoint tab carries X-Webhook-Test: true. Its payment_method.id and transaction_id resolve to nothing, and its merchant_id is yours.