Payment sources
Turn a card or Nequi token into a long-lived payment source you can re-charge.
A payment source is Wompi’s way of storing a tokenized card or Nequi account against a customer. Once created, you can re-charge it by passing its numeric id into createTransaction — no further tokenization or acceptance handshake needed.
createPaymentSource(input)
Promote a one-time token into a reusable source. You’ll need fresh acceptance tokens from merchants.getMerchant() — Wompi treats this as a separate customer consent.
// 1. Tokenize the card (or Nequi account) up-front.
const [tokenError, token] = await wompi.tokens.tokenizeCard({
number: "4242424242424242",
cvc: "123",
exp_month: "12",
exp_year: "29",
card_holder: "PEDRO PEREZ",
});
if (tokenError) throw tokenError;
// 2. Fetch fresh acceptance tokens from the merchant resource.
const [merchantError, merchant] = await wompi.merchants.getMerchant();
if (merchantError) throw merchantError;
const acceptanceToken = merchant.presigned_acceptance?.acceptance_token;
const personalAuthToken =
merchant.presigned_personal_data_auth?.acceptance_token;
if (!acceptanceToken || !personalAuthToken)
throw new Error("Merchant has no acceptance tokens");
// 3. Convert the card token into a long-lived payment source.
const [error, response] = await wompi.paymentSources.createPaymentSource({
type: "CARD",
token: token.id,
acceptance_token: acceptanceToken,
accept_personal_auth: personalAuthToken,
customer_email: "buyer@example.com",
payment_description: "Suscripcion mensual",
});
if (error) throw error;
response.id; // numeric id — store this against your user
Input
| Field | Type | Notes |
|---|---|---|
type |
string |
"CARD", "NEQUI", "DAVIPLATA" or "BANCOLOMBIA_TRANSFER". |
token |
string |
Output of tokens.tokenizeCard / tokenizeNequi. |
acceptance_token |
string |
merchant.presigned_acceptance.acceptance_token. |
accept_personal_auth |
string |
merchant.presigned_personal_data_auth.acceptance_token — the second consent. |
customer_email |
email |
The customer this source belongs to. |
payment_description |
string? |
Text the customer sees when they approve the source, e.g. in the Nequi push message. |
Any other field Wompi documents also reaches the API — the SDK does not strip unknown keys from this payload.
getPaymentSource(id)
Look a payment source up by its numeric id.
const [error, response] = await wompi.paymentSources.getPaymentSource(12_345);
if (error) throw error;
response.id;
response.status; // "AVAILABLE", "PENDING" or "VOIDED"
response.type; // "CARD", "NEQUI", "DAVIPLATA" or "BANCOLOMBIA_TRANSFER"
Response
| Field | Type | Notes |
|---|---|---|
id |
number |
Stable, persist this against your user. |
status |
string |
"AVAILABLE", "PENDING" (Nequi, until the customer approves) or "VOIDED". |
type |
string? |
"CARD", "NEQUI", "DAVIPLATA" or "BANCOLOMBIA_TRANSFER". |
token |
string? |
The underlying token. |
customer_email |
string? |
Owning customer. |
public_data |
object? |
{ type, phone_number? } — safe to surface in the UI. |
Charging a stored source
Drop the id into createTransaction as payment_source_id. Note the change in auth — using payment_source_id requires the private key, not the public one.
const [error, response] = await wompi.transactions.createTransaction({
acceptance_token,
accept_personal_auth,
amount_in_cents: 990_000,
currency: "COP",
signature,
customer_email: "buyer@example.com",
reference: `recur-${Date.now()}`,
payment_source_id: 12_345, // ← reusing the stored source
});