Pasar a producción

Prueba todo con pagos simulados y pasa a cobrar de verdad cambiando solo la configuración.

Para cuando tu integración ya funciona en prueba y vas a recibir pagos reales. La idea es que pasar a producción no toque tu código: solo variables de entorno y recursos creados otra vez en el otro entorno.

El modelo

PruebaProducción
Clave secretaEmpieza por sk_test_Empieza por sk_prod_
SDKenvironment: "test"environment: "production"
PagosSimulados, con escenarios conocidosReales: mueven dinero
Productos, planes, clientesLos de pruebaOtros, creados en producción
WebhookSu endpoint y su secretoOtro endpoint, con otro secreto
  • Dos entornos aislados. Nada pasa de uno a otro: un ID de prueba no existe en producción. Por eso tu código busca planes y productos por su lookupKey, que sí puede repetirse en cada entorno, en vez de guardar IDs.
  • La misma validación en los dos. Los datos que pide cada método de pago y cómo se validan son iguales; en prueba solo cambia el cobro real por un simulador. Lo que funciona en prueba funciona en producción.
  • La clave dice su entorno. El SDK rechaza al crearse una clave que no coincide con environment, así que una configuración mezclada falla al arrancar y no al cobrar.

1. Prueba con pagos simulados

Con una clave sk_test_, cada método del checkout trae escenarios de prueba: qué datos enviar para que el pago se confirme, falle por un motivo concreto o se quede esperando. El checkout alojado los muestra; en un checkout propio vienen en testScenarios.

Recorre al menos una compra exitosa, un pago rechazado y su reintento, un evento repetido y, si vendes suscripciones, una renovación y una cancelación. La lista completa está en prueba tu integración.

2. Configura el entorno por variables

import { createBillete } from "@boelabs/billete-sdk";

// Lee la clave de BILLETE_API_KEY.
export const billete = createBillete({
  apiVersion: "2026-10-24",
  environment: process.env.BILLETE_ENVIRONMENT === "production" ? "production" : "test",
});

En el servidor de producción, BILLETE_API_KEY tiene la clave sk_prod_ (de Desarrolladores → Claves API, con el dashboard en producción) y BILLETE_ENVIRONMENT vale production. La clave nunca va en el navegador ni dentro de una app móvil: ahí se usa el cliente público.

3. Crea tus recursos en producción

Productos, planes, cuotas, cupones y enlaces de pago se crean otra vez, con el dashboard en producción o con un script que corres una vez. A planes y productos dales el mismo lookupKey que en prueba y búscalos por él; las cuotas ya se identifican por su key:

const { data: [plus] } = await billete.plans.list({ lookupKey: "plus" });
const { data: [camiseta] } = await billete.products.list({ lookupKey: "camiseta_negra" });

Los clientes no se copian: se crean solos con sus primeras compras o suscripciones en producción.

4. Registra el webhook de producción

const endpoint = await billete.webhookEndpoints.create({
  url: "https://tuapp.com/api/webhooks/billete",
  events: ["checkout.completed", "subscription.updated", "subscription.renewed"],
});
// Guarda `endpoint.secret` en el servidor de producción: no es el de prueba.

En producción la URL debe ser HTTPS y pública. Cómo recibir los eventos sin perder ni duplicar ninguno está en webhooks sin perder ni duplicar.

5. Revisa la lista

  • Versión fija. apiVersion es obligatoria en el SDK y Billete nunca cambia una versión publicada: tu integración se comporta igual hasta que tú la actualices. El endpoint del webhook tiene su propia versión; mantenla igual a la del SDK (versiones).
  • Idempotencia en lo que cobra o devuelve. El SDK genera una clave por llamada, pero si tu código repite una operación (un job que reintenta, un doble clic), pasa una idempotencyKey derivada de lo tuyo, como checkout-${order.id} (idempotencia).
  • Errores por código. Decide según error.code, nunca según el mensaje, y guarda error.requestId para soporte. Si una llamada se cortó (network_error), consulta el estado antes de repetirla:
import { BilleteError } from "@boelabs/billete-sdk";

try {
  await billete.subscriptions.create(input, { idempotencyKey: `hobby-${user.id}` });
} catch (error) {
  if (error instanceof BilleteError && error.code === "subscription_exists") return;
  throw error;
}
  • Entrega por webhook, no por la página de éxito. El cliente puede abrir successUrl sin haber pagado; entrega al recibir checkout.completed.
  • Eventos del entorno correcto. Tu ruta de webhooks comprueba event.environment antes de procesar.

6. Activa tu negocio

Para operar en producción, tu negocio debe completar su verificación en el dashboard y estar aprobado. Hasta entonces, una petición con una clave sk_prod_ responde production_not_enabled. Prueba no necesita aprobación: está disponible siempre.

7. Haz el primer pago real

Con todo desplegado, haz una compra real pequeña y comprueba el monto en bolívares, que llegue el webhook, que tu aplicación entregue la compra y que el pago aparezca en el dashboard. Desde aquí, cada operación mueve dinero real.

Prueba tu integración · Autenticación · Configuración del SDK · Errores y reintentos