Eventos y webhooks
El gateway expone el flujo de eventos y los webhooks del core con sus propias rutas /v1. La semántica (entrega al menos una vez, deduplicación por eid, firma HMAC) es la descrita en Eventos y webhooks del core.
La entrega depende de que el banco tenga activos el outbox de eventos y el despachador de webhooks. Con el outbox apagado los lotes llegan vacíos. Confírmalo durante la incorporación.
Leer eventos libremente
Alcance events:read.
curl -s -i "https://gateway.banco.example/v1/events?limit=100&eventTypes=AccEntryPosted,TransactionPosted" \
-H "Authorization: Bearer $TOKEN"
El cuerpo es { "cursor": "…", "events": [ … ] } y el gateway copia además el cursor siguiente a la cabecera Items-Next-Cursor. Para continuar, pásalo en ?cursor=. Sin cursor, la lectura empieza en el primer evento conservado. limit va de 1 a 1000.
Suscripciones con cursor confirmado
Alcance events:read. El servidor guarda tu posición: si tu consumidor se reinicia, retoma donde confirmó.
# Crear (201, o 200 si ya existe una con la misma identidad)
curl -s -X POST https://gateway.banco.example/v1/subscriptions \
-H "Authorization: Bearer $TOKEN" -H "Idempotency-Key: $(uuidgen)" -H "Content-Type: application/json" \
-d '{ "owningApplication": "conciliador-erp", "eventTypes": ["AccEntryPosted"], "readFrom": "begin" }'
# Leer el lote siguiente (siempre desde el cursor confirmado; no admite ?cursor=)
curl -s -i "https://gateway.banco.example/v1/subscriptions/1b2c3d4e-5f60-4a7b-8c9d-0e1f2a3b4c5d/events?limit=100" \
-H "Authorization: Bearer $TOKEN"
# Confirmar lo procesado
curl -s -X POST https://gateway.banco.example/v1/subscriptions/1b2c3d4e-5f60-4a7b-8c9d-0e1f2a3b4c5d/cursors \
-H "Authorization: Bearer $TOKEN" -H "Content-Type: application/json" \
-d '{ "cursor": "48213-1052" }'
| Respuesta de la confirmación | Significado |
|---|---|
200 {"committed": true, …} | Cursor avanzado. |
200 {"committed": false, …} | El cursor era igual o anterior al confirmado; no es un error. |
409 | Hay otra confirmación concurrente. |
422 | El cursor va por delante del flujo. |
Enviar ?cursor= en la lectura de una suscripción responde 400 CURSOR_NO_ADMITIDO. Las suscripciones se consultan y borran con GET y DELETE /v1/subscriptions/{subscriptionId}.
Webhooks
Registrar (alcance webhooks:write):
curl -s -X POST https://gateway.banco.example/v1/webhooks \
-H "Authorization: Bearer $TOKEN" -H "Idempotency-Key: $(uuidgen)" -H "Content-Type: application/json" \
-d '{
"name": "ERP contable",
"url": "https://erp.example.com/finora/webhooks",
"eventTypes": ["AccEntryPosted", "TransactionPosted"]
}'
La respuesta 201 trae secret, que se muestra una sola vez (Cache-Control: no-store). Las entregas las hace el core directamente a tu URL, firmadas como se explica en Verificar la firma.
| Operación | Ruta | Alcance |
|---|---|---|
| Listar | GET /v1/webhooks?offset=0&limit=50 | webhooks:read |
| Consultar | GET /v1/webhooks/{webhookId} | webhooks:read |
Reemplazar (también para rotar el secreto con "rotateSecret": true) | PUT /v1/webhooks/{webhookId} | webhooks:write |
| Eliminar | DELETE /v1/webhooks/{webhookId} | webhooks:write |
| Reactivar entregas tras fallos seguidos | POST /v1/webhooks/{webhookId}:reset-circuit | webhooks:write |
| Buscar entregas | POST /v1/webhooks/deliveries:search con {subscriptionId, status, eventType, from, to}; status es PENDING, DELIVERED, FAILED o DEAD | webhooks:read |
| Reenviar una entrega | POST /v1/webhooks/deliveries/{deliveryId}:resend (202; 409 si ya hay una pendiente) | webhooks:write |