Skip to content

El modelo de montos

La guía que hay que leer antes de escribir cualquier aritmética. Todo lo que sigue existe porque la alternativa es un error de factor cien o mil que ninguna validación puede detectar: los dos números son montos válidos, así que nada falla, y la primera señal es el saldo equivocado de un cliente.

Todo monto es un entero

No hay decimales en ninguna parte de esta API. 100000000 no son cien millones de nada: son esa cantidad de unidades mínimas del activo al que pertenece.

unidades enteras = amountMinor / 10 ** assetDecimals

El punto flotante no toca un monto en ninguna dirección. Si tu lenguaje tiene un entero lo bastante grande, úsalo; si no, usa su decimal de precisión arbitraria. Un 1000.5 en un cuerpo JSON no es algo que esta API acepte, y un float que llega como 9999.999999998 es un ticket de soporte que nadie puede cerrar.

Los decimales son del activo, y no son los que esperas

Lee assetDecimals de la respuesta

Nunca lo fijes en tu código, y nunca lo deduzcas del símbolo.

ActivoDecimales aquíLo que quizá asumiste
USDT46
COPM22
USDC66

USDT es la trampa. La convención en cadena son seis decimales; el mercado reporta cuatro, y esta API reporta lo que el mercado reporta. Una integración que fije seis enviará la centésima parte de lo que pretende, siempre, y todos los montos seguirán siendo montos válidos.

El mismo activo podría en principio reformularse. Leer el campo no cuesta nada y te inmuniza.

Un ejemplo completo

Tu organización tiene 10 000 USDT y quiere saber cuánto vale en pesos.

json
{ "assetSymbol": "USDT", "assetDecimals": 4, "amountMinor": 100000000 }
100000000 / 10^4 = 10 000 USDT

Pides una cotización y recibes:

json
{ "rateQuoteMinor": 316500, "amountBaseMinor": 100000000, "amountQuoteMinor": 31650000000 }

rateQuoteMinor está en unidades mínimas del activo quote por cada unidad entera del base. COPM lleva dos decimales, así que 316500 / 10^2 = 3 165,00 COPM por USDT. Y:

31650000000 / 10^2 = 316 500 000 COPM

No recalcules amountQuoteMinor por tu cuenta para compararlo. Usa el número de la respuesta.

El redondeo ya está decidido, y no es simétrico

La plataforma redondea a la baja lo que recibes y al alza lo que pagas. Es deliberado: el residuo es de la casa, y una regla de redondeo que a veces favoreciera al cliente haría que los libros dejaran de cuadrar de una forma que después nadie podría explicar.

La consecuencia práctica: las cifras de una cotización son las cifras. Rederivarlas a partir de la tasa te dará de vez en cuando un número a una unidad mínima de distancia, y el equivocado será el tuyo.

Una tasa no es un precio reutilizable

Un rateQuoteMinor pertenece a la cotización en la que vino. Refleja un momento, un tamaño y las condiciones de tu organización. Guardarla y aplicarla a otro monto produce un número que la plataforma no va a honrar — y, peor, uno que tus usuarios ya vieron.

Si necesitas mostrar una tasa en vivo, pide una cotización. Son gratis y no comprometen a nada.

Lista de verificación

  • [ ] Ningún float ni double toca un monto, en ningún sitio
  • [ ] assetDecimals viene de la API, nunca de una constante
  • [ ] Muestras amountMinor / 10 ** assetDecimals, y envías la inversa
  • [ ] Nunca rederivas un monto que la API ya te dio
  • [ ] Tus pruebas incluyen USDT con cuatro decimales, que es el que rompe