API Thestral
- Versión
1.0.0- URL base
https://api.nerivia.io/v1/thestral/neripay
Guía
Introducción
Thestral es la API REST de Nerivia para integraciones externas: un solo host HTTPS, cuerpos JSON y un mismo esquema de firma para todos los productos. Nerivia no es custodial: nunca retiene tus fondos.
Autenticación
Thestral no usa tokens bearer: cada solicitud va firmada, así nadie puede reenviarla ni alterarla. Cada clave de API tiene dos valores:
api_key_uuid: el ID público de la clave, que envías en cada solicitud.api_key_signing_secret: el secreto con el que firmas. Se muestra una sola vez, al crear la clave, y nunca vuelve a enviarse a Nerivia.
Envía estos tres encabezados en cada solicitud:
| Encabezado | Valor |
|---|---|
X-Nerivia-Key-Id |
Tu api_key_uuid. |
X-Nerivia-Timestamp |
La hora Unix actual, en segundos. |
X-Nerivia-Signature |
El HMAC-SHA256 del mensaje firmado, en hexadecimal y minúsculas, con tu api_key_signing_secret como clave. |
El mensaje firmado es la marca de tiempo, un punto y el cuerpo exacto de la solicitud, en UTF-8:
<timestamp>.<raw_body>
- Firma exactamente los bytes que envías. Cualquier diferencia, incluso un espacio o el orden de las claves, invalida la firma.
- Una solicitud sin cuerpo firma solo
<timestamp>. - La marca de tiempo debe estar a menos de cinco minutos de la hora del servidor, así que mantén tu reloj sincronizado.
Una firma inválida, una marca de tiempo desfasada, una clave revocada o expirada, o un
espacio suspendido devuelven 401 con un código de error específico. Revoca una clave
o define su vencimiento en el panel de Nerivia.
Espacios de trabajo
Un espacio de trabajo reúne tu configuración, tus claves de API y tus pedidos, y nada pasa de un espacio a otro. Cada cuenta tiene dos:
- Producción: pagos reales.
- Pruebas: los mismos flujos en redes de prueba, para ensayar tu integración.
Cada clave de API pertenece a un solo espacio, y Nerivia lo identifica a partir de esa clave: ninguna URL ni cuerpo lo nombra. Para pasar de pruebas a producción, firma con la clave del otro espacio.
Errores
Todos los errores tienen la misma forma:
{
"errors": [
{
"code": "neripay_order_amount_out_of_range",
"field": null,
"message": "El monto del pedido está fuera del rango aceptado."
}
]
}code: un ID estable y legible por máquinas. Basa tu lógica en él, nunca en el mensaje.field: el campo de la solicitud que causó el error, onull.message: una explicación legible en el idioma deAccept-Language, inglés o español.
La lista errors trae un elemento por cada problema. El código de estado indica el
tipo de falla: 400 para una solicitud inválida, 401 para una falla de
autenticación, 403 para una falta de permisos y 404 para un objeto al que hace
referencia la solicitud y que no existe en tu espacio.
Webhooks
En vez de consultar la API una y otra vez, registra la URL de tu endpoint en el panel y elige los eventos que quieres recibir. Cada suscripción tiene su propio secreto de firma.
Nerivia envía un POST con un cuerpo JSON a tu endpoint, firmado igual que una
solicitud: X-Nerivia-Timestamp y X-Nerivia-Signature, calculados sobre el cuerpo
exacto con el secreto de esa suscripción. Verifica la firma antes de confiar en un
envío y responde con cualquier estado 2xx para confirmarlo. Si respondes con otro
estado o no respondes a tiempo, Nerivia reintenta un número limitado de veces.
Soporte
¿Necesitas ayuda? Escríbenos por WhatsApp al +593 963 187 317.
Recurso
Configuraciones de activo y red
Una configuración de activo y red es un activo en una red blockchain (ledger) que tu espacio acepta, como USDT en Polygon, con su dirección de recepción, su comisión y sus montos mínimo y máximo. Las configuras en el panel y la API las consulta.
GETListar configuraciones de activo y red
/workspace-config/asset-ledger-configs/Devuelve las configuraciones activas de tu espacio, de la más reciente a la más antigua: cada par de activo y red en el que puedes crear pedidos ahora mismo. Las inactivas nunca aparecen y ningún filtro las incluye.
Filtra por activo o por red con los UUID dentro del objeto asset_ledger de un
elemento, nunca con el uuid de la configuración. Si usas varios filtros, se
aplican todos a la vez. Un valor que la API no puede leer, como un UUID mal
formado, devuelve una lista vacía, nunca la lista sin filtrar.
Un espacio sin configuraciones activas recibe un 200 con la lista results
vacía: configura una en el panel antes de crear pedidos.
Solicitud
Parámetros
assetstring (uuid)Solo configuraciones de este
uuidde activo, en cada red donde esté configurado.ledgerstring (uuid)Solo configuraciones en este
uuidde red, para cada activo configurado en ella.limitintegerElementos por página. Por defecto,
10, valor que también se usa si el que envías no es válido.offsetintegerElementos que se omiten antes de empezar la página. Por defecto,
0, valor que también se usa si el que envías no es válido.
Respuestas
200
Tus configuraciones de activo y red activas.
countintegerElementos que coinciden con tus filtros, en todas las páginas.
nextstring | null (uri)URL de la página siguiente, o
nullen la última.previousstring | null (uri)URL de la página anterior, o
nullen la primera.resultsarrayLos elementos de esta página, del más reciente al más antiguo.
uuidstringEl ID de la configuración. No es el valor que envías al crear un pedido.
is_activebooleanSi el par acepta pedidos. Aquí siempre es
true.commission_ratestring (decimal)La comisión de Nerivia en porcentaje:
"2.50"significa 2.50%. Cada pedido nuevo conserva la tasa vigente al crearse.min_amountstring (decimal)El monto mínimo aceptado por pedido, en unidades del activo.
max_amountstring (decimal)El monto máximo aceptado por pedido, en unidades del activo.
receiving_addressstringLa dirección a la que se envía tu parte de cada pedido liquidado. Revísala después de cualquier cambio en el panel.
asset_ledgerobjectEl activo y la red de esta configuración.
uuidstringID del par de activo y red. Envíalo como
asset_ledgeral crear un pedido.contract_addressstring | nullLa dirección del contrato del token en esta red, o
nullsi es el activo nativo de la red. No es donde paga el cliente.assetobjectEl activo, como Tether USD.
uuidstringEl ID del activo.
namestringEl nombre del activo, como Tether USD.
codestringEl código del activo, como
USDT.decimalsintegerLos decimales que admite el activo, que limitan la precisión del monto de un pedido.
ledgerobjectLa red blockchain (ledger), como Polygon.
uuidstringEl ID de la red.
namestringEl nombre de la red, como Polygon Amoy.
codestringEl código de la red, como
polygon-amoy.address_regexstring | nullEl patrón que debe cumplir una dirección en esta red, o
nullsi no se conoce.
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"uuid": "59a13b02-a4b5-4d42-9d20-19d42be990e9",
"is_active": true,
"commission_rate": "2.50",
"min_amount": "1.000000000000000000",
"max_amount": "10000.000000000000000000",
"receiving_address": "0xf59fedB5D38CD00995AC1D8256f4CfeF46FD58a3",
"asset_ledger": {
"uuid": "37caa3f8-79f3-48a3-bde2-840636f50df2",
"contract_address": "0x0502986e4Be5d3e0A98D68A0fD0f7683F9968843",
"asset": {
"uuid": "46588bb4-600b-4e41-a5c0-95071166f41d",
"name": "Tether USD",
"code": "USDT",
"decimals": 2
},
"ledger": {
"uuid": "85a198fd-4ee6-4f17-bbeb-040ff46896dc",
"name": "Polygon Amoy",
"code": "polygon-amoy",
"address_regex": "^0x[0-9a-fA-F]{40}$"
}
}
}
]
}401
Falló la autenticación: firma inválida, marca de tiempo desfasada, clave revocada o expirada, o espacio suspendido.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
403
La clave no tiene permiso para esta acción.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
Recurso
Pedidos
Un pedido le pide a un cliente pagar un monto en un activo sobre una red, a una dirección exclusiva de ese pedido. Pasa por estos estados por sí solo:
| Estado | Significado |
|---|---|
awaiting_payment |
Creado y en espera del pago del cliente hasta expires_at. |
paid |
Pago confirmado en la blockchain. Entrega el pedido en este punto. |
settling |
Nerivia está enviando los fondos a tu dirección de recepción. |
completed |
Los fondos llegaron a tu dirección de recepción. |
expired |
No llegó ningún pago antes de expires_at. |
settlement_failed |
Falló el envío de los fondos a tu dirección de recepción. |
Suscríbete al evento de webhook neripay.order.status.change para seguir estos
cambios, o consulta Listar pedidos con el uuid del pedido como filtro.
GETListar pedidos
/orders/Devuelve los pedidos de tu espacio, del más reciente al más antiguo.
Filtra por created_at con los dos parámetros de fecha, que incluyen sus
límites; la respuesta no incluye ese campo. Si usas varios filtros, se aplican
todos a la vez. Un valor que la API no puede leer, como un UUID mal formado,
devuelve una lista vacía, nunca la lista sin filtrar.
Los elementos de la lista no traen checkout_url: tómalo de la respuesta de
creación.
Solicitud
Parámetros
statusstringSolo pedidos en este estado.
uuidstring (uuid)Solo el pedido con este ID.
created_at__gtestring (date-time)Solo pedidos creados en este momento o después. Un valor sin zona horaria se interpreta en UTC.
created_at__ltestring (date-time)Solo pedidos creados en este momento o antes. Un valor sin zona horaria se interpreta en UTC.
limitintegerElementos por página. Por defecto,
10, valor que también se usa si el que envías no es válido.offsetintegerElementos que se omiten antes de empezar la página. Por defecto,
0, valor que también se usa si el que envías no es válido.
Respuestas
200
Tus pedidos.
countintegerElementos que coinciden con tus filtros, en todas las páginas.
nextstring | null (uri)URL de la página siguiente, o
nullen la última.previousstring | null (uri)URL de la página anterior, o
nullen la primera.resultsarrayLos elementos de esta página, del más reciente al más antiguo.
uuidstringEl ID del pedido. Guárdalo para encontrar el pedido después con el filtro
uuid.amountstring (decimal)Lo que paga el cliente, en unidades del activo. La comisión de Nerivia se descuenta de este monto, no se suma.
commission_ratestring (decimal)La comisión de Nerivia en porcentaje, fijada al crear el pedido.
statusstringEl estado actual del pedido, como
awaiting_paymentopaid.expires_atstring (date-time)Cuándo deja de aceptar pagos el pedido. Basa tu cuenta regresiva en este valor en vez de asumir un plazo fijo.
contract_addressstringLa dirección de liquidación propia del pedido, donde paga el cliente. Úsala solo para este pedido.
asset_ledgerobjectEl activo y la red en que se cobra el pedido.
uuidstringID del par de activo y red.
assetobjectEl activo, como Tether USD.
uuidstringEl ID del activo.
namestringEl nombre del activo, como Tether USD.
codestringEl código del activo, como
USDT.decimalsintegerLos decimales que admite el activo, que limitan la precisión del monto de un pedido.
ledgerobjectLa red blockchain (ledger), como Polygon.
uuidstringEl ID de la red.
namestringEl nombre de la red, como Polygon Amoy.
codestringEl código de la red, como
polygon-amoy.address_regexstring | nullEl patrón que debe cumplir una dirección en esta red, o
nullsi no se conoce.
contract_addressstring | nullLa dirección del contrato del token en esta red, o
nullsi es el activo nativo de la red. No es donde paga el cliente.
external_referencestring | nullTu propio ID del pedido, o
nullsi se creó desde el panel.
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"uuid": "e75f7105-d903-4d69-b1ea-17bbfbd7f777",
"amount": "10.000000000000000000",
"commission_rate": "2.50",
"status": "settlement_failed",
"expires_at": "2026-09-11T05:44:18.988829Z",
"contract_address": "0x0146a0AA378044be8a59e2aee97B00Cac073539C",
"asset_ledger": {
"uuid": "37caa3f8-79f3-48a3-bde2-840636f50df2",
"asset": {
"uuid": "46588bb4-600b-4e41-a5c0-95071166f41d",
"name": "Tether USD",
"code": "USDT",
"decimals": 2
},
"ledger": {
"uuid": "85a198fd-4ee6-4f17-bbeb-040ff46896dc",
"name": "Polygon Amoy",
"code": "polygon-amoy",
"address_regex": "^0x[0-9a-fA-F]{40}$"
},
"contract_address": "0x0502986e4Be5d3e0A98D68A0fD0f7683F9968843"
},
"external_reference": null
}
]
}401
Falló la autenticación: firma inválida, marca de tiempo desfasada, clave revocada o expirada, o espacio suspendido.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
403
La clave no tiene permiso para esta acción.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
POSTCrear pedido
/orders/Crea un pedido de pago por un monto en un activo sobre una red. Nerivia le asigna
al pedido su propia dirección de liquidación, empieza a vigilarla y devuelve el
pedido con un checkout_url: una página de pago alojada a la que puedes enviar a
tu cliente en lugar de crear la tuya.
Un pedido nuevo empieza en awaiting_payment, y su plazo de pago comienza en
cuanto esta llamada tiene éxito.
Después de crearlo
Muéstrale a tu cliente contract_address y amount, o envíalo a
checkout_url. Nerivia confirma el pago, marca el pedido como paid, envía los
fondos a tu dirección de recepción y lo marca como completed, sin que tengas
que hacer otra llamada.
Entrega el pedido al llegar a paid, no a completed: paid significa que tu
cliente ya pagó, y completed solo indica que los fondos ya te llegaron.
Solicitud
Cuerpo
El pedido que se va a crear. Los tres campos son obligatorios y cualquier otro campo se ignora.
asset_ledgerstringObligatorioEl
asset_ledger.uuidde una configuración de activo y red activa en el espacio de tu clave.amountstring (decimal)ObligatorioLo que paga el cliente, como decimal en texto y en unidades del activo, por ejemplo
"25.50". Debe estar entre elmin_amounty elmax_amountde la configuración, no tener más decimales de los que admite el activo y tener como máximo 36 dígitos y 18 decimales.external_referencestringObligatorioTu propio ID del pedido, como un número de factura. Hasta 36 caracteres y único en tu espacio, así un reintento nunca duplica un cobro.
{
"asset_ledger": "37caa3f8-79f3-48a3-bde2-840636f50df2",
"amount": "100.00",
"external_reference": "AAA-000-000-003"
}Respuestas
201
El pedido creado.
uuidstringEl ID del pedido. Guárdalo para encontrar el pedido después con el filtro
uuid.amountstring (decimal)Lo que paga el cliente, en unidades del activo. La comisión de Nerivia se descuenta de este monto, no se suma.
commission_ratestring (decimal)La comisión de Nerivia en porcentaje, fijada al crear el pedido.
statusstringEl estado actual del pedido, como
awaiting_paymentopaid.expires_atstring (date-time)Cuándo deja de aceptar pagos el pedido. Basa tu cuenta regresiva en este valor en vez de asumir un plazo fijo.
contract_addressstringLa dirección de liquidación propia del pedido, donde paga el cliente. Úsala solo para este pedido.
asset_ledgerobjectEl activo y la red en que se cobra el pedido.
uuidstringID del par de activo y red.
assetobjectEl activo, como Tether USD.
uuidstringEl ID del activo.
namestringEl nombre del activo, como Tether USD.
codestringEl código del activo, como
USDT.decimalsintegerLos decimales que admite el activo, que limitan la precisión del monto de un pedido.
ledgerobjectLa red blockchain (ledger), como Polygon.
uuidstringEl ID de la red.
namestringEl nombre de la red, como Polygon Amoy.
codestringEl código de la red, como
polygon-amoy.address_regexstring | nullEl patrón que debe cumplir una dirección en esta red, o
nullsi no se conoce.
contract_addressstring | nullLa dirección del contrato del token en esta red, o
nullsi es el activo nativo de la red. No es donde paga el cliente.
external_referencestringTu propio ID del pedido, tal como lo enviaste.
checkout_urlstring (uri)Una página de pago alojada por Nerivia solo para este pedido, que puedes compartir con tu cliente.
{
"uuid": "9ba6ade8-416a-495b-8cf6-6eeac215ab08",
"amount": "100.000000000000000000",
"commission_rate": "2.50",
"status": "awaiting_payment",
"expires_at": "2026-09-11T21:45:03.204571Z",
"contract_address": "0x23BDBDbAD94Bb5CD2D8AD44645523D4A5Bd1aeD9",
"asset_ledger": {
"uuid": "37caa3f8-79f3-48a3-bde2-840636f50df2",
"asset": {
"uuid": "46588bb4-600b-4e41-a5c0-95071166f41d",
"name": "Tether USD",
"code": "USDT",
"decimals": 2
},
"ledger": {
"uuid": "85a198fd-4ee6-4f17-bbeb-040ff46896dc",
"name": "Polygon Amoy",
"code": "polygon-amoy",
"address_regex": "^0x[0-9a-fA-F]{40}$"
},
"contract_address": "0x0502986e4Be5d3e0A98D68A0fD0f7683F9968843"
},
"external_reference": "AAA-000-000-001",
"checkout_url": "https://app.nerivia.io/neripay/checkout/9ba6ade8-416a-495b-8cf6-6eeac215ab08"
}400
La solicitud no es válida. errors lista cada problema.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
{
"errors": [
{
"code": "neripay_order_amount_out_of_range",
"field": null,
"message": "El monto del pedido está fuera del rango aceptado."
}
]
}401
Falló la autenticación: firma inválida, marca de tiempo desfasada, clave revocada o expirada, o espacio suspendido.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
403
La clave no tiene permiso para esta acción.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.
404
Un objeto al que hace referencia la solicitud no existe en tu espacio.
errorsarrayUn elemento por cada problema.
codestringUn ID de error estable y legible por máquinas. Basa tu lógica en él, nunca en
message.fieldstring | nullEl campo de la solicitud que causó el error, o
null.messagestringUna explicación legible en el idioma de
Accept-Language.