Conceptos Clave
La integración PSE en Kamin usa un ciclo de vida de intent fijo, dos modelos de comercio y dos Effects para entregar los resultados del pago. Entiende estos conceptos antes de implementar los handlers.
Términos específicos de PSE
| Término | Descripción |
|---|---|
pseUrl | La URL del portal bancario del cliente. Se retorna en el proof registered. Tu aplicación redirige al cliente a esta URL para autorizar el pago. |
trazabilityCode | Número de trazabilidad PSE (CUS — Código Único de Seguimiento) asignado por PSE para la transacción. Disponible en el proof registered. Mismo valor que coreId — son alias del mismo número bajo nombres distintos. |
coreId | Número de trazabilidad PSE para la transacción. Disponible en el proof prepared. Mismo valor que trazabilityCode — son alias del mismo número bajo nombres distintos. Úsalo como referencia de recibo final para el cliente. |
bankCode | El código de institución financiera PSE que identifica el banco del cliente (e.g., "1007" para Bancolombia). Se incluye en el campo source.custom.bankCode del intent. |
pcop | El handle del Symbol para el peso colombiano en Kamin Ledger. Siempre usa pcop como símbolo en los intents PSE. |
pse-bridge | Identificador del servicio interno de Kamin que se comunica con PSE en tu nombre. Aparece como signer: "pse-bridge" en los proofs firmados por Kamin. Nunca llamas a PSE directamente. |
Ciclo de vida del Intent
Un intent PSE atraviesa las siguientes etapas. Cada etapa la registra un actor específico como un proof firmado sobre el intent. Algunas etapas son valores que toma el campo meta.status del intent; otras (registered, confirmed) sólo viven en meta.proofs[].custom.status y no propagan al meta.status del intent.
| Etapa | Aparece en | Establecido por | Significado |
|---|---|---|---|
pending | meta.status | Tu backend (firma inicial) | Intent creado y enviado. Aún no existe transacción PSE. |
registered | meta.proofs[].custom.status | Kamin | Kamin registró la transacción en PSE. pseUrl y trazabilityCode están disponibles. Redirige al cliente ahora. |
confirmed | meta.proofs[].custom.status (opcional) | Tu backend (página de retorno) | Le avisas a Kamin que el cliente regresó del banco. Acelera la resolución del intent, pero no es obligatorio: si el cliente no regresa al sitio, Kamin igual consulta a PSE de forma asíncrona y el intent llegará a prepared o rejected por su cuenta — solo que tarda más. |
prepared | meta.status | Kamin | PSE confirmó el pago. coreId está disponible. Muestra al cliente una pantalla de éxito. |
committed | meta.status | Kamin | Movimiento en el ledger iniciado — los fondos están siendo acreditados. |
completed | meta.status | Kamin | Liquidación final. La wallet del cliente ha sido acreditada con pcop. |
rejected | meta.status | Kamin | Fallo final. El intent no será reintentado. Puede ocurrir en dos fases: en la creación (PSE rechaza antes de entregar pseUrl) o en el procesamiento de la transacción (tras confirmed, si PSE no autoriza). Consulta Referencia de Errores — PSE para las tablas de códigos detail y Manejar Webhooks para el recorrido del historial de proofs. |
pending ──▶ registered ──▶ confirmed ──▶ prepared ──▶ committed ──▶ completed
│ │
└──▶ rejected └──▶ rejected
(en la creación) (en el procesamiento de la transacción)registered y confirmed no cambian el meta.status del intent. Son proofs específicos del flujo PSE con un custom.status propio que notifica cambios dentro de la transacción PSE.
prepared y completed son estados distintos. prepared significa que PSE confirmó la transacción — aquí llega el coreId y es cuando debes mostrar al cliente una pantalla de éxito. completed significa que Kamin Ledger ejecutó el movimiento y acreditó pcop a tu wallet del cliente.
Modelos de comercio
Las integraciones PSE soportan dos modelos de comercio. Ambos comparten la misma estructura base del intent; el modelo agregador agrega un bloque custom.subMerchant. El modelo determina qué campos identifican al comercio final y qué serviceCode enviar.
Comercio directo
Tu negocio es el comercio de registro. La wallet del cliente (target) es el comercio final que recibe el pago — PSE enruta los fondos directamente a ella.
target.custom lleva tu identidad: identificationType, identificationNumber, name, ciiuCategory, y tu propio serviceCode asignado por Kamin. No hay bloque custom.subMerchant.
Agregador
Operas en nombre de un sub-comercio downstream. La wallet del cliente (target) sigue recibiendo los fondos, pero PSE trata custom.subMerchant como el comercio final de registro de la transacción.
Omite target.custom.name — se reemplaza por custom.subMerchant.name. Agrega el bloque completo custom.subMerchant con la identidad del sub-comercio. Envía tu propio serviceCode asignado como agregador en target.custom.serviceCode, no el del sub-comercio.
El target.custom.ciiuCategory (tu CIIU) y custom.subMerchant.ciiuCategory (el CIIU del sub-comercio) son independientes — pueden tener valores distintos.
Consulta la guía Cobrar un Pago para la referencia completa del payload en ambos modelos.
Estructura de Effects
Kamin configura dos Effects en el ledger para cada integración PSE. Los Effects son reglas en el ledger que observan intents y envían señales HTTP a tu URL de webhook cuando llega un proof que coincide con su filtro.
| Effect | Handle | Se dispara en | Señal de webhook |
|---|---|---|---|
| 1 | pse-intent-progress@<dominio> | Proof registered, proof prepared (dos entregas separadas) | intent-proofs-added |
| 2 | pse-intent-completion@<dominio> | Proof completed o intent rejected | intent-proofs-added (completed) / intent-updated (rejected) |
Ambos effects son configurados por Kamin durante el onboarding usando las mismas llamadas REST descritas en Registrar y Escuchar Effects de Estado de Intent. La única diferencia es el filtro aplicado a cada effect.
Siguiente paso
Con esto ya tienes claro el modelo PSE en Kamin y el ciclo de vida completo del intent. En la siguiente sesión continuaremos con Cómo obtener los bancos activos, donde obtendrás la lista de instituciones financieras habilitadas que tu formulario de checkout debe ofrecer al cliente.
Historial de cambios
- Agregado• Version inicial