EKIA Data Service

Errores y límites

El contrato de errores es estable: códigos fijos, un formato único y una señal explícita de si conviene reintentar. Esta página es la tabla completa de la plataforma; cada servicio enlaza aquí y solo agrega la forma de sus códigos propios.

El formato

Todo error responde el mismo body. Respuesta real de un request sin token:

Respuesta real (2026-09-28).

{
  "code": "UNAUTHORIZED",
  "message": "missing bearer token",
  "request_id": "c95a96e7-1636-40ac-b422-24c0f88030fc",
  "retryable": false
}

Programe contra code, que es contractual; message es descriptivo y puede mejorar con el tiempo. retryable indica si el mismo request puede tener éxito al reintentarse sin cambiar nada: true solo en RATE_LIMITED, DOWNLOAD_QUOTA, INTERNAL y SERVICE_UNAVAILABLE; los tres con Retry-After dicen cuánto esperar.

Los códigos

La columna dominio marca los códigos que solo un servicio produce; el resto es de la plataforma y puede aparecer en cualquier endpoint.

code HTTP dominio cuándo ocurre
INVALID_PARAMS 400 todos Parámetro faltante o mal formado, from > to, rango mayor a 5 años, as_of_revision fuera de rango, RUC que no tiene 11 dígitos, o page_token corrupto o de otra consulta.
UNAUTHORIZED 401 todos Token ausente, inválido, revocado o expirado. El servicio nunca repite el token en la respuesta.
FORBIDDEN 403 todos El token no puede usar esa ruta: un token de colector en /v1; GET /v1/ruc/by-dni/{dni} mientras el prerrequisito legal E1 esté pendiente; la descarga de un artefacto del padrón con un token sin la marca descarga_artefactos (Consulta RUC).
UNSUPPORTED_CURRENCY 404 tipo de cambio Moneda que la API sabe que no sirve (ejemplo real: currency=EUR).
UNSUPPORTED_SERIES 404 tipo de cambio Serie distinta de publicado y cierre.
NO_OBSERVATIONS 404 tipo de cambio, revisiones Consulta válida pero sin observaciones: rango sin datos o serie aún sin cobertura (Tipo de cambio); en /v1/revisions, at anterior a la primera revisión. Distinto por diseño de UNSUPPORTED_CURRENCY: "no hay datos" no es "no sirvo esa moneda".
NOT_FOUND 404 todos Observación, evidencia o artefacto inexistente para el id pedido.
NO_DATA_AT_REVISION 404 consulta RUC La as_of_revision pedida es anterior a la primera publicación del dominio (Consulta RUC). Todo dominio con publicaciones lo hereda.
RATE_LIMITED 429 todos Límite de requests del token excedido. Trae Retry-After con los segundos a esperar.
DOWNLOAD_QUOTA 429 todos Cuota diaria de bytes de descarga del token agotada (/v1/evidence/{id}/descarga). Trae Retry-After.
INTERNAL 500 todos Error interno. El detalle queda en los registros del servicio (referenciable por request_id), nunca en el body.
SERVICE_UNAVAILABLE 503 todos La base de datos no está disponible (por ejemplo, durante un reinicio). Trae Retry-After.

Un dominio nuevo que necesite un código propio lo declara en esta tabla antes de producirlo; el registro de cambios fecha cada alta.

Límites de uso

Cuota de descarga

Los bytes de evidencia (GET /v1/evidence/{id}/descarga) tienen una cuota diaria por token, aparte del límite de requests:

cuota bytes por día
por token 20 GB (propuesto a partir del egreso medido del archivo: 19,8 MB/s; equivale a unos 50 ZIP del padrón al día)
credencial de evaluación interna 2 GB (unos cinco ZIP del padrón)

La ventana es deslizante de 24 horas. Una captura pequeña (el tipoCambio.txt) cuenta por sus bytes al servirse; un artefacto grande (el ZIP del padrón) cuenta por su tamaño al emitirse el redirect, y se rechaza con DOWNLOAD_QUOTA si no cabe entero en lo que queda. Los metadatos (GET /v1/evidence/{id}) nunca cuentan. La descarga es parte del plan del token, sin sobrecargo.

Paginación a revisión fija

Dos endpoints paginan, con el mismo mecanismo:

endpoint máximo por página orden
GET /v1/rates 366 ítems fecha ascendente
GET /v1/ruc/{ruc}/history 500 transiciones ordinal ascendente

Si hay más, viene next_page_token: un token opaco que lleva embebida la revisión de la primera página y la consulta a la que pertenece; se pasa en page_token.

Límite adicional: el rango from–to de tasas no puede exceder 5 años por consulta.

Caché

respuesta política
Respuesta anclada a revisión (as_of_revision, page_token) del tipo de cambio immutable + ETag (SHA-256 del body) — cacheable indefinidamente.
/v1/rates, /v1/rates/latest sin anclar no-store — el dataset puede avanzar; no la guarde.
/v1/ruc/{ruc}, by-dni, /history, /v1/ruc-coverage y /v1/evidence/{sha256} (metadatos del padrón), ancladas o no private, no-store, sin ETag, Vary: Authorization salvo ruc-coverage (adenda a ESP-006 A.7, desde R0): cada respuesta lleva valores propios del pedido. If-None-Match: * sobre un 200 → 304 sin cuerpo y con los mismos encabezados; otro valor → 200; un error se responde aunque traiga la precondición. La estabilidad del contenido anclado es propiedad del dato, no de la caché.
/v1/evidence/{id}/descarga de una captura del tipo de cambio immutable + ETag = SHA-256 de los bytes.
/v1/evidence/{uuid} (metadatos de una captura) no-store — el enlace firmado cambia en cada emisión.
/v1/observations/{id} no-store — la observación es inmutable, pero su representación incluye la cadena de supersesión y los eventos, que pueden crecer.

Alertas y salud: la plataforma se vigila a sí misma

Estos endpoints valen para todo dominio y no tienen página de servicio: