Autentica
Intercambia client_id y client_secret por un access_token temporal.
POST /v1/auth/verify
Autenticación, creación de cobros on-chain, checkout y webhooks con los contratos reales de la API de negocios.
La API de Buyesia Business permite a tu servidor crear órdenes de cobro en stablecoins, entregar una URL de checkout al comprador y recibir la confirmación por webhooks firmados.
La API es servidor a servidor. Autentica con tus credenciales de integración (client_id y client_secret) desde el portal de negocios, obtén un token temporal y úsalo como Bearer en cada solicitud.
Intercambia client_id y client_secret por un access_token temporal.
POST /v1/auth/verify
Define monto, moneda y red. Recibes el order_id y la checkout_url.
POST /v1/transactions
Recibe payment_order.paid firmado y concilia tu pedido interno.
payment_order.paid
Este es el flujo mínimo para pasar de credenciales a un checkout funcionando.
curl --request POST 'https://business.buyesia.com/api/v1/auth/verify' \
--header 'Content-Type: application/json' \
--data '{
"client_id": "{client_id}",
"client_secret": "{client_secret}"
}'
<?php
$payload = [
'client_id' => getenv('BUYESIA_CLIENT_ID'),
'client_secret' => getenv('BUYESIA_CLIENT_SECRET'),
];
$ch = curl_init('https://business.buyesia.com/api/v1/auth/verify');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ['Content-Type: application/json'],
CURLOPT_POSTFIELDS => json_encode($payload),
]);
$response = json_decode(curl_exec($ch), true);
$token = $response['data']['access_token'] ?? null;
const response = await fetch('https://business.buyesia.com/api/v1/auth/verify', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
client_id: process.env.BUYESIA_CLIENT_ID,
client_secret: process.env.BUYESIA_CLIENT_SECRET,
}),
});
const { data } = await response.json();
const token = data.access_token;
{
"status": true,
"message": "Token emitido correctamente.",
"data": {
"access_token": "6f1c...9e21",
"token_type": "Bearer",
"mode": "live",
"expires_at": "2026-09-10T18:32:11+00:00"
}
}
Intercambia tus credenciales de integración por un token temporal para llamar al resto de la API.
Puedes obtenerlo una vez y reutilizarlo hasta que expire. No requiere token previo.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
client_id |
string | Sí | Identificador público de tu credencial. |
client_secret |
string | Sí | Secreto de tu credencial. No lo expongas en el navegador. |
curl --request POST 'https://business.buyesia.com/api/v1/auth/verify' \
--header 'Content-Type: application/json' \
--data '{
"client_id": "{client_id}",
"client_secret": "{client_secret}"
}'
<?php
$payload = [
'client_id' => getenv('BUYESIA_CLIENT_ID'),
'client_secret' => getenv('BUYESIA_CLIENT_SECRET'),
];
$ch = curl_init('https://business.buyesia.com/api/v1/auth/verify');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ['Content-Type: application/json'],
CURLOPT_POSTFIELDS => json_encode($payload),
]);
$response = json_decode(curl_exec($ch), true);
$token = $response['data']['access_token'] ?? null;
const response = await fetch('https://business.buyesia.com/api/v1/auth/verify', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
client_id: process.env.BUYESIA_CLIENT_ID,
client_secret: process.env.BUYESIA_CLIENT_SECRET,
}),
});
const { data } = await response.json();
const token = data.access_token;
{
"status": true,
"message": "Token emitido correctamente.",
"data": {
"access_token": "6f1c...9e21",
"token_type": "Bearer",
"mode": "live",
"expires_at": "2026-09-10T18:32:11+00:00"
}
}
Genera la intención de cobro, resuelve la wallet destino y devuelve la URL de checkout para el comprador.
Requiere Authorization: Bearer {access_token}. La moneda debe estar habilitada y la red debe ser una de las redes soportadas.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
amount |
number | Sí | Monto mayor a 0. |
currency |
string | Sí | Moneda habilitada: USDT o USDC. |
chain |
string | Sí | Red on-chain: POLYGON, ETH, BASE, ARBITRUM, BSC o AVALANCHE. |
order_no |
string | No | Identificador externo de tu orden. |
description |
string | No | Descripción visible del cobro. |
success_url |
string | No | URL de retorno cuando el pago se completa. |
cancel_url |
string | No | URL de retorno cuando el pago se cancela. |
webhook_url |
string | No | URL puntual que recibe los eventos de esta orden. |
metadata |
object | No | Objeto libre que se conserva y reenvía en el webhook. |
curl --request POST 'https://business.buyesia.com/api/v1/transactions' \
--header 'Authorization: Bearer {access_token}' \
--header 'Content-Type: application/json' \
--data '{
"amount": 25.50,
"currency": "USDT",
"chain": "POLYGON",
"order_no": "ORD-2026-1042",
"description": "Suscripción Pro",
"success_url": "https://tu-tienda.com/pago/exito",
"cancel_url": "https://tu-tienda.com/pago/cancelado",
"webhook_url": "https://tu-tienda.com/webhooks/buyesia",
"metadata": { "customer_id": "cus_128" }
}'
<?php
$ch = curl_init('https://business.buyesia.com/api/v1/transactions');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => [
'Content-Type: application/json',
'Authorization: Bearer ' . $token,
],
CURLOPT_POSTFIELDS => json_encode([
'amount' => 25.50,
'currency' => 'USDT',
'chain' => 'POLYGON',
'order_no' => 'ORD-2026-1042',
'description' => 'Suscripción Pro',
'success_url' => 'https://tu-tienda.com/pago/exito',
'cancel_url' => 'https://tu-tienda.com/pago/cancelado',
]),
]);
$order = json_decode(curl_exec($ch), true)['data'];
header('Location: ' . $order['checkout_url']);
const response = await fetch('https://business.buyesia.com/api/v1/transactions', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${token}`,
},
body: JSON.stringify({
amount: 25.5,
currency: 'USDT',
chain: 'POLYGON',
order_no: 'ORD-2026-1042',
}),
});
const { data } = await response.json();
console.log(data.order_id, data.checkout_url);
{
"status": true,
"message": "Orden de pago creada.",
"data": {
"order_id": "8f3c1d2a-...-a91d",
"order_no": "ORD-2026-1042",
"amount": 25.5,
"currency": "USDT",
"chain": "POLYGON",
"destination_address": "0x2b...7c",
"status": "pending",
"mode": "live",
"description": "Suscripción Pro",
"checkout_url": "https://business.buyesia.com/checkout/{checkout_token}",
"created_at": "2026-09-10T17:32:11+00:00",
"paid_at": null,
"payment": null,
"checkout_token": "e7d1...4b"
}
}
Devuelve el estado actual de la orden y, si ya fue pagada, el detalle del pago confirmado.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
order_id |
string | Sí | UUID de la orden devuelto al crearla (parámetro de ruta). |
curl --request GET 'https://business.buyesia.com/api/v1/transactions/{order_id}' \
--header 'Authorization: Bearer {access_token}'
<?php
$ch = curl_init('https://business.buyesia.com/api/v1/transactions/{order_id}');
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . $token],
]);
$order = json_decode(curl_exec($ch), true)['data'];
{
"status": true,
"data": {
"order_id": "8f3c1d2a-...-a91d",
"status": "paid",
"amount": 25.5,
"currency": "USDT",
"chain": "POLYGON",
"paid_at": "2026-09-10T17:41:02+00:00",
"payment": {
"reference": "pay_9f31...",
"net_amount": 25.5,
"chain": "POLYGON",
"tx_hash": "0x7b4f...9e21"
}
}
}
Cancela una orden que todavía está pendiente y dispara el evento payment_order.cancelled.
Solo se pueden cancelar órdenes en estado pending.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
order_id |
string | Sí | UUID de la orden pendiente (parámetro de ruta). |
curl --request POST 'https://business.buyesia.com/api/v1/transactions/{order_id}/cancel' \
--header 'Authorization: Bearer {access_token}'
<?php
$ch = curl_init('https://business.buyesia.com/api/v1/transactions/{order_id}/cancel');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . $token],
]);
$order = json_decode(curl_exec($ch), true)['data'];
{
"status": true,
"message": "Orden cancelada.",
"data": {
"order_id": "8f3c1d2a-...-a91d",
"status": "cancelled",
"currency": "USDT",
"chain": "POLYGON"
}
}
El comprador interactúa con la checkout_url devuelta al crear la orden. Esta API alimenta la app Buyesia Pay.
No necesitas construir el checkout: al crear la orden recibes checkout_url y rediriges al comprador allí. La app consulta este endpoint para mostrar el detalle y luego confirma el pago on-chain.
La respuesta incluye checkout_app_url, el deep link buyesia://business/checkout/{checkout_token} que abre la app Buyesia Pay directamente en la pantalla de pago.
Este endpoint requiere un token de usuario de Buyesia Pay (auth:api-v2), no las credenciales del negocio.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
checkout_token |
string | Sí | Token contenido en checkout_url (parámetro de ruta). |
curl --request GET 'https://business.buyesia.com/api/v2/business/checkout/{checkout_token}' \
--header 'Authorization: Bearer {user_access_token}'
{
"status": true,
"data": {
"order_id": "8f3c1d2a-...-a91d",
"amount": 25.5,
"currency": "USDT",
"chain": "POLYGON",
"destination_address": "0x2b...7c",
"status": "pending",
"checkout_url": "https://business.buyesia.com/checkout/{checkout_token}",
"checkout_app_url": "buyesia://business/checkout/{checkout_token}",
"merchant": "Mi Comercio"
}
}
Verifica el recibo en la blockchain y marca la orden como pagada cuando la transferencia es válida.
La verificación comprueba el recibo, el origen, el destino y el monto exacto antes de aceptar el pago.
| Campo | Tipo | Req. | Descripción |
|---|---|---|---|
tx_hash |
string | Sí | Hash de la transacción (0x + 64 caracteres hex). |
chain |
string | Sí | Red donde se realizó la transferencia. |
sender_address |
string | Sí | Wallet de origen (0x + 40 caracteres hex). |
curl --request POST 'https://business.buyesia.com/api/v2/business/checkout/{checkout_token}/confirm' \
--header 'Authorization: Bearer {user_access_token}' \
--header 'Content-Type: application/json' \
--data '{
"tx_hash": "0x7b4f...9e21",
"chain": "POLYGON",
"sender_address": "0x91a2...33f0"
}'
{
"status": true,
"message": "Pago on-chain confirmado.",
"data": {
"order_id": "8f3c1d2a-...-a91d",
"order_status": "paid",
"reference": "pay_9f31...",
"amount": 25.5,
"currency": "USDT",
"chain": "POLYGON",
"tx_hash": "0x7b4f...9e21",
"paid_at": "2026-09-10T17:41:02+00:00"
}
}
Registra endpoints en la sección Webhooks del portal. Cada entrega incluye el cuerpo JSON y dos cabeceras: X-Business-Event y X-Business-Signature.
X-Business-EventNombre del evento entregado.
X-Business-SignatureHMAC SHA-256 del cuerpo JSON crudo con el secreto del webhook.
| Evento | Descripción |
|---|---|
payment_order.created |
La orden fue creada y está pendiente de pago. |
payment_order.paid |
La transferencia fue verificada on-chain. |
payment_order.cancelled |
La orden fue cancelada antes de pagarse. |
{
"event": "payment_order.paid",
"data": {
"order_id": "8f3c1d2a-...-a91d",
"order_no": "ORD-2026-1042",
"amount": 25.5,
"currency": "USDT",
"chain": "POLYGON",
"status": "paid",
"mode": "live",
"paid_at": "2026-09-10T17:41:02+00:00",
"payment": {
"reference": "pay_9f31...",
"net_amount": 25.5,
"chain": "POLYGON",
"tx_hash": "0x7b4f...9e21"
}
},
"sent_at": "2026-09-10T17:41:03+00:00"
}
<?php
$rawBody = file_get_contents('php://input');
$signature = $_SERVER['HTTP_X_BUSINESS_SIGNATURE'] ?? '';
$secret = getenv('BUYESIA_WEBHOOK_SECRET');
$expected = hash_hmac('sha256', $rawBody, $secret);
if (!hash_equals($expected, $signature)) {
http_response_code(401);
exit;
}
$event = json_decode($rawBody, true);
$type = $event['event'] ?? null;
$data = $event['data'] ?? [];
if ($type === 'payment_order.paid') {
// Marca tu pedido como pagado usando $data['order_no'] o $data['order_id'].
}
http_response_code(200);
echo json_encode(['received' => true]);
La API responde con JSON uniforme. Los errores de validación devuelven 422 con el detalle por campo y los de autenticación 401.
| Código | Nombre | Descripción |
|---|---|---|
| 200 | OK | Solicitud procesada correctamente. |
| 201 | Created | Orden creada correctamente. |
| 401 | No autorizado | Token ausente, inválido o expirado. |
| 404 | Not found | La orden solicitada no pertenece a tu cuenta. |
| 422 | Unprocessable entity | Datos inválidos: moneda o red no habilitada, monto incorrecto, etc. |
| 429 | Too many requests | Has superado el límite de solicitudes. Reintenta con backoff. |