Errores
El formato de error de Auvral, cada código de estado que devuelve la API y qué hacer con cada uno.
Cada respuesta de error tiene la misma forma:
{
"statusCode": 409,
"message": "Flow has no published version",
"code": "FLOW_NOT_PUBLISHED"
}| Campo | Descripción |
|---|---|
statusCode | Repite el código de estado HTTP. |
message | Legible para una persona. Escrito para un desarrollador que lee un log, no es un código estable legible por máquina. Nunca ramifiques según esta cadena. |
code | Un código estable y legible por máquina para la condición. Está presente en todos los errores que devuelve la API excepto el 500. Ramifica según este campo. |
code es contra lo que escribes tu manejo de errores; message puede reescribirse en
cualquier momento. El campo no aparece cuando no hay código que dar, así que léelo como
opcional.
Un código que ya existe nunca cambia de significado.
Las respuestas exitosas usan el mismo sobre, con data en lugar de message:
{ "statusCode": 201, "data": { "sessionId": "..." } }El catálogo de POST /v1/sessions
400 Bad request
El cuerpo no validó. Estos son errores de tu integración; reintentar la misma petición no va a ayudar.
code | Causa |
|---|---|
MISSING_REQUIRED_FIELDS | Falta flowId o está vacío |
INVALID_REFERENCE_ID | Enviaste referenceId pero no es un string, o está vacío (o solo tiene espacios, se recorta). Omite el campo por completo si quieres que Auvral asigne uno |
REFERENCE_ID_TOO_LONG | referenceId supera los 128 caracteres. Acórtalo, o aplícale un hash a tu identificador |
INVALID_METADATA | metadata incumple uno de sus límites: 50 claves como máximo, claves de 1 a 40 caracteres, valores string de 500 caracteres como máximo, sin anidamiento. El message nombra la regla que falló |
INVALID_EXPIRES_IN | expiresIn no es un entero, no es positivo, o supera 86400 |
INVALID_ALLOWED_ORIGINS | Una entrada de allowedOrigins no es un origen http/https ni "*": falta el esquema, trae ruta, query, barra final, o el host va en mayúsculas. También cubre "*" enviado junto a un origen concreto, más de 20 entradas, y una entrada de más de 255 caracteres. El message nombra la entrada culpable y la forma canónica que sí se habría aceptado |
INVALID_RETURN_URL | returnUrl no es una URL absoluta http o https, o supera los 2048 caracteres. Una ruta relativa, un host sin esquema y cualquier otro esquema (javascript:, data:) se rechazan |
INVALID_FLOW_VERSION | flowVersion no es published ni draft |
DRAFT_REQUIRES_SANDBOX_KEY | Se envió flowVersion: "draft" con una llave de live. Los borradores solo se pueden probar en sandbox |
401 Unauthorized
{ "statusCode": 401, "message": "Invalid api key", "code": "INVALID_API_KEY" }Siempre exactamente este cuerpo, sin importar qué salió mal: falta, está mal formada, es desconocida, fue revocada, o se usó contra el ambiente equivocado. Recorre la lista de comprobación en Autenticación.
403 Forbidden
code | Causa |
|---|---|
PLAN_EXHAUSTED | Tu plan se quedó sin verificaciones de live, o su ventana gratuita terminó. El message dice cuál de las dos fue |
Solo se rechazan las llaves de live: las verificaciones de sandbox no se cuentan y nunca se acaban, así que puedes seguir probando tu integración con el plan agotado. No se creó nada, y la misma petición funciona apenas se amplíe el plan. Escríbenos a sales@auvral.com, o revisa el plan en la página Mi plan del dashboard.
404 Not found
code | Causa |
|---|---|
FLOW_NOT_FOUND | El flowId no existe, o pertenece a una organización distinta de la de tu llave de API |
FLOW_DRAFT_NOT_FOUND | Pediste flowVersion: "draft" y el flujo no tiene cambios sin publicar |
La causa más común de FLOW_NOT_FOUND es cruzar ambientes: un id de flujo de sandbox
enviado con una llave de live, o al revés. Los ids de flujo no se comparten entre
ambientes.
409 Conflict
El flujo existe, y no puede correr en este momento. Ambos casos se arreglan en el dashboard, no en tu petición.
code | Causa |
|---|---|
FLOW_NOT_PUBLISHED | El flujo nunca se publicó, así que no hay versión publicada que correr. Publícalo, o pide flowVersion: "draft" con una llave de sandbox |
FLOW_NOT_ACTIVE | El flujo fue desactivado. No acepta sesiones nuevas con ninguno de los dos tipos de llave hasta que se reactive |
Las sesiones que ya creaste no se ven afectadas: cada una fija la versión del flujo con la que abrió, y la corre hasta el final pase lo que pase con el flujo después.
500 Server error
{ "statusCode": 500, "message": "Failed to create session" }Algo salió mal del lado de Auvral, y no lleva code: un error del servidor no es una
condición para ramificar. Reintenta con backoff. Si persiste, escríbenos e incluye la
marca de tiempo y el referenceId que enviaste.
El catálogo de las lecturas
Las dos lecturas responden un solo 404 para cada razón por la que un id no es tuyo, y
nunca dicen cuál de esas razones fue.
GET /v1/sessions/{sessionId}
code | Estado | Causa |
|---|---|---|
SESSION_NOT_FOUND | 404 | Ninguna sesión con ese id pertenece a tu llave: nunca existió, es de otra organización, se creó en el otro ambiente, o expiró sin que tu usuario la empezara |
INVALID_API_KEY | 401 | El mismo cuerpo que en todas partes |
Una sesión que expiró después de que tu usuario la empezó no es un 404: responde
200 con el veredicto, reconstruido a partir de la verificación que produjo. Solo
desaparece la sesión que no dejó nada detrás.
GET /v1/verifications/{id}
code | Estado | Causa |
|---|---|---|
VERIFICATION_NOT_FOUND | 404 | Ninguna verificación con ese id pertenece a tu llave: id desconocido, otra organización, o el otro ambiente |
INVALID_API_KEY | 401 | El mismo cuerpo que en todas partes |
Aquí también el cruce de ambientes es la causa común: un verificationId de sandbox leído
con una llave live es un 404, y al revés también.
Reintentos
| Estado | ¿Reintentar? |
|---|---|
| 400 | No, corrige la petición |
| 401 | No, corrige la credencial |
| 403 | No, primero hay que ampliar el plan |
| 404 | No, corrige el id |
| 409 | No, corrige el flujo en el dashboard |
| 500 | Sí, con backoff exponencial |
POST /v1/sessions no es idempotente: referenceId nombra a la persona, no a la llamada, así que no es una llave de idempotencia, y cada llamada exitosa crea una sesión nueva.
Un reintento después de una llamada que en realidad sí funcionó deja atrás una sesión sin usar, lo cual es inofensivo porque expira sola, pero no reintentes a menos que tengas confianza en que la primera llamada no funcionó.
Errores que no son errores de la API
Una verificación rechazada no es un error. verification.failed llega con un 200
desde tu endpoint y significa que las comprobaciones no pasaron. Ver
Referencia de eventos.
Los errores del SDK son aparte. onError({ code, message }) reporta problemas de
integración en el navegador (missing_url, already_open) y nunca lleva el resultado de
una verificación. Ver Referencia del SDK.
Una URL expirada falla en el navegador, no en tus llamadas a la API: tu usuario ve un mensaje de expiración y tu backend no recibe aviso. La recuperación es una sesión nueva.