# API REST

> Consultar los datos de tu contact center desde otros sistemas

## Qué es la API REST de Audara

La API REST te permite consultar los datos históricos de tu contact center desde tus propios sistemas: el detalle de las llamadas que atendieron tus agentes, los abandonos de cada cola, las sesiones de trabajo y las pausas. Es de solo lectura y todos sus endpoints responden en JSON.

Sirve para alimentar un tablero de BI, cruzar la operación con tu CRM o construir informes propios con reglas que la plataforma no trae. Si lo que buscas es lo contrario, que Audara consulte un servicio tuyo durante una conversación, eso es otro módulo y lo explica [Integraciones REST](https://docs.audara.io/integraciones-api-rest/).

- **URL base**: https://rest.audara.io/v1
- **Protocolo**: HTTPS únicamente. La API no acepta conexiones sin cifrar.
- **Formato**: JSON con codificación UTF-8.
- **Métodos**: Solo GET. La API no modifica datos.

> **Nota**
> Los datos que devuelve la API son los mismos que ves en [Reportes](https://docs.audara.io/reportes/). Si una cifra no te cuadra con la del informe en pantalla, revisa primero el rango de fechas y la zona horaria, porque la API siempre trabaja en UTC.

## Pedir tus credenciales

Necesitas dos datos para usar la API, y los entrega el equipo de soporte de Audara al activar tu acceso. No se generan desde el panel de administración.

- **Tenant Key**: Identifica a tu organización dentro de Audara. Viaja en el header `X-Tenant-Key`.
- **Token de acceso**: Tu credencial. Viaja en el header `Authorization` con el prefijo `Bearer`.

Al solicitar el acceso, ten a mano las direcciones IP desde las que vas a consultar. Cada organización tiene una lista de IPs autorizadas y las peticiones que llegan desde otra dirección se rechazan, así que si tu servidor cambia de IP hay que avisar a soporte.

> **Importante**
> Trata el token como una contraseña. No lo pongas en el código de una aplicación web ni en un repositorio, porque cualquiera que lo tenga puede leer los datos de tu operación. Si crees que se filtró, pide a soporte que lo revoque.

## Tu primera petición

Los dos headers van en todas las peticiones. Sin ellos, la solicitud se rechaza antes de consultar nada.

```
`curl -X GET "https://rest.audara.io/v1/call/history?queue_name=Ventas&date_from=2026-08-01&date_to=2026-08-31" \
  -H "X-Tenant-Key: tu-tenant-key" \
  -H "Authorization: Bearer tu-token-de-acceso"`
```

Todas las respuestas tienen la misma forma: un arreglo `data` con los registros y un objeto `pagination` con el estado del recorrido.

```
`{
  "data": [ ... ],
  "pagination": {
    "page": 1,
    "limit": 50,
    "has_more": true
  }
}`
```

## Paginación

Todos los endpoints devuelven resultados por páginas, ordenados del más reciente al más antiguo. Los controlas con dos parámetros opcionales.

| Parámetro | Por defecto | Máximo | Descripción |
| --- | --- | --- | --- |
| `page` | 1 | sin tope | Número de página. Empieza en 1. |
| `limit` | 50 | 200 | Registros por página. |

Para recorrer un rango completo, mira el campo `has_more`. Cuando viene en `true` quedan registros por leer: suma 1 a `page` y repite la petición con los mismos filtros. Cuando viene en `false`, ya llegaste al final.

> **Nota**
> La respuesta no incluye un total de registros. Es a propósito: contar el universo completo en cada petición sería lento sobre operaciones grandes. Usa `has_more` para saber si continuar, no un total.

## Fechas y rango máximo

Los endpoints de llamadas y de agentes exigen `date_from` y `date_to`, y aceptan dos formatos.

| Formato | Ejemplo | Cómo se interpreta |
| --- | --- | --- |
| Solo fecha | `2026-08-15` | `date_from` se ancla a las 00:00:00.000 y `date_to` a las 23:59:59.999, para que el día entero quede incluido. |
| Fecha y hora | `2026-08-15T08:30:00Z` | Se usa exactamente el valor que envías. |

La API opera en UTC y no convierte zonas horarias. Si necesitas filtrar por hora local, manda la fecha con su desplazamiento explícito, por ejemplo `2026-08-15T00:00:00-05:00`.

> **Importante**
> El rango máximo entre `date_from` y `date_to` es de **31 días**. Así un mes calendario completo cabe en una sola consulta. Si te pasas, recibes un error `DATE_RANGE_TOO_LARGE`. Para traer un periodo más largo, pártelo por meses.

## Límites de uso

La API aplica cuatro controles de tasa, y cualquiera de ellos puede frenarte. Estos son los valores por defecto, que tu organización puede tener ajustados.

| Control | Ámbito | Límite por defecto |
| --- | --- | --- |
| Por IP | Dirección desde la que consultas | 10 peticiones por minuto |
| Por token | Tu credencial | 300 peticiones por minuto |
| Por organización | Todos tus tokens juntos | 15 peticiones por minuto |
| Por organización, al día | Todos tus tokens juntos | 2 500 peticiones al día |

Cuando superas alguno, la respuesta es un `429` y trae el header `Retry-After` con los segundos que debes esperar. Respétalo en lugar de reintentar de inmediato.

> **Buenas prácticas**
> El límite más estrecho es el de 10 peticiones por minuto por IP, así que pide páginas de 200 registros en lugar de páginas pequeñas: es la misma información con veinte veces menos peticiones. Y si sincronizas todos los días, guarda lo que ya trajiste y consulta solo el día nuevo.

## Errores

Todos los errores llegan con la misma estructura, de modo que puedes manejarlos con un solo bloque de código.

```
`{
  "statusCode": 400,
  "error": "Bad Request",
  "message": "Descripción legible del problema",
  "code": "DATE_RANGE_TOO_LARGE"
}`
```

- **statusCode**: El código HTTP, repetido dentro del cuerpo.
- **error**: El nombre HTTP del error, por ejemplo Bad Request o Unauthorized.
- **message**: La descripción del problema, escrita para que la lea una persona. Puede cambiar de una versión a otra, así que no construyas lógica sobre este texto.
- **code**: El identificador estable del error. Es el campo sobre el que conviene programar, cuando está presente.

Estos son los códigos que puedes recibir según la situación.

| HTTP | Situación | Campo `code` |
| --- | --- | --- |
| 400 | Falta el header `X-Tenant-Key` o viene vacío. | no viene |
| 400 | Un parámetro de consulta falta o tiene un valor inválido. | `FST_ERR_VALIDATION` |
| 400 | `date_from` es posterior a `date_to`, o una fecha no es válida. | `INVALID_DATE_RANGE` |
| 400 | El rango supera los 31 días. | `DATE_RANGE_TOO_LARGE` |
| 401 | El token falta, tiene un formato inválido, no se reconoce, fue revocado, expiró, o no corresponde a la organización indicada. | no viene |
| 403 | La IP desde la que consultas no está autorizada. | no viene |
| 403 | Tu organización está suspendida. | no viene |
| 404 | La ruta no existe. | no viene |
| 429 | Superaste un límite de uso. Revisa `Retry-After`. | no viene |
| 500 | Error interno. | `INTERNAL` |

> **Importante**
> Los errores de autenticación no traen el campo `code`, así que para distinguirlos tienes que mirar el `statusCode` y el `message`. Y un `401` no te dice cuál de las causas se dio: eso es deliberado, para no confirmarle a un atacante si un token existe. Al depurar, revisa las dos credenciales y la IP.

## Llamadas atendidas

`GET /v1/call/history` devuelve las llamadas que entraron a una cola y fueron atendidas por un agente. Es la base para medir productividad, tiempos de atención y conversión. Equivale al detalle que ves en [Reportes de Inbound](https://docs.audara.io/reportes-inbound/).

| Parámetro | Requerido | Descripción |
| --- | --- | --- |
| `queue_name` | Sí | Nombre exacto de la campaña, tal como está configurada. Distingue mayúsculas. |
| `date_from` | Sí | Inicio del rango. |
| `date_to` | Sí | Fin del rango. |
| `page` | No | Página. Por defecto 1. |
| `limit` | No | Registros por página. Por defecto 50, máximo 200. |

Cada registro trae estos campos. Cualquiera puede llegar en `null` si el dato no quedó registrado en esa llamada.

- **queue_name**: Campaña en la que se atendió la llamada.
- **group_name**: Grupo de trabajo al que pertenecía el agente durante la llamada.
- **group_oid**: Identificador numérico de ese grupo.
- **agent_number**: Número del agente que atendió.
- **agent_name**: Nombre del agente.
- **extension**: Extensión desde la que atendió.
- **phone**: Número de teléfono de quien llamó. Puede venir vacío si la llamada no lo entregó.
- **call_start_date**: Fecha y hora en que empezó la llamada, en UTC.
- **call_end_date**: Fecha y hora en que terminó.
- **duration**: Duración total de la llamada, en segundos.
- **queue_waiting**: Segundos que el cliente esperó en la cola antes de que un agente contestara.
- **hold_time**: Segundos que el agente dejó al cliente en espera durante la llamada.
- **acw_duration**: Segundos que el agente ocupó en el trabajo posterior a la llamada.
- **acw_time**: Tiempo de trabajo posterior permitido, en segundos. Es un valor de configuración, no algo que ocurrió.
- **acw_alarm_time**: Segundos en los que el trabajo posterior **excedió** el tiempo permitido. Viene en 0 cuando el agente no se pasó.
- **conversion**: Si la llamada se marcó como conversión.
- **conversion_goal**: Si se alcanzó el objetivo de conversión definido.
- **wsresult**: Resultado del webservice asociado a la campaña, cuando la campaña usa uno.

```
`{
  "data": [
    {
      "queue_name": "Ventas",
      "group_name": "Equipo A",
      "group_oid": 35,
      "agent_number": 1021,
      "agent_name": "Laura Toro",
      "extension": 1021,
      "phone": "573001234567",
      "call_start_date": "2026-08-15T09:32:11.000Z",
      "call_end_date": "2026-08-15T09:38:45.000Z",
      "duration": 394,
      "queue_waiting": 18,
      "hold_time": 0,
      "acw_duration": 45,
      "acw_time": 60,
      "acw_alarm_time": 0,
      "conversion": true,
      "conversion_goal": false,
      "wsresult": ""
    }
  ],
  "pagination": { "page": 1, "limit": 50, "has_more": false }
}`
```

> **Importante**
> Fíjate en la diferencia entre `acw_time` y `acw_alarm_time`, porque el segundo nombre engaña: no es un umbral configurado sino los segundos que el agente se pasó. El umbral es `acw_time`. Para contar cuántas llamadas excedieron el trabajo posterior, cuenta las que tengan `acw_alarm_time` mayor que 0.

## Llamadas abandonadas

`GET /v1/call/abandon` devuelve las llamadas que entraron a una cola y se cortaron antes de que un agente las tomara. Sirve para medir la tasa de abandono y detectar las horas en las que la demanda supera a tu equipo.

Recibe los mismos parámetros que el endpoint anterior: `queue_name`, `date_from` y `date_to` son obligatorios, y `page` y `limit` opcionales.

- **queue_name**: Campaña en la que ocurrió el abandono.
- **event**: Tipo de evento registrado, por ejemplo ABANDON.
- **hold_time**: Segundos que el cliente esperó antes de colgar.
- **event_time**: Fecha y hora del abandono, en UTC.
- **call_id**: Identificador de la llamada. Te sirve para cruzarla con tus grabaciones o con el detalle de la central.
- **created_at**: Fecha y hora en que se guardó el registro. Suele ser uno o dos segundos después del evento.

```
`{
  "data": [
    {
      "queue_name": "Soporte",
      "event": "ABANDON",
      "hold_time": 127,
      "event_time": "2026-08-15T14:22:08.000Z",
      "call_id": "1710512528.4831",
      "created_at": "2026-08-15T14:22:09.000Z"
    }
  ],
  "pagination": { "page": 1, "limit": 50, "has_more": true }
}`
```

> **Nota**
> Para calcular una tasa de abandono necesitas los dos endpoints: los abandonos de `/call/abandon` y las atendidas de `/call/history`, sobre el mismo rango y la misma campaña. La API no entrega el total de llamadas ofrecidas en un solo campo.

## Sesiones de los agentes

`GET /v1/agent/login` devuelve los inicios y cierres de sesión de un agente. Con esto calculas horas conectadas, puntualidad y adherencia al turno, que es lo mismo que mide [WFM](https://docs.audara.io/wfm/) dentro de la plataforma.

| Parámetro | Requerido | Descripción |
| --- | --- | --- |
| `agent_number` | Sí | Número del agente. Es un entero positivo. |
| `date_from` | Sí | Inicio del rango. |
| `date_to` | Sí | Fin del rango. |
| `page` | No | Página. Por defecto 1. |
| `limit` | No | Registros por página. Por defecto 50, máximo 200. |

- **agent_number, agent_name, extension**: Identificación del agente.
- **group_name y group_id**: Grupo de trabajo durante la sesión, por nombre y por identificador.
- **queue_name y queue_id**: Campaña en la que estuvo conectado.
- **dialer_name**: Marcador asignado, cuando la sesión fue de campaña saliente.
- **agent_level**: Nivel del agente dentro de la plataforma.
- **login_time**: Momento del inicio de sesión, en UTC.
- **logout_time**: Momento del cierre de sesión.
- **duration**: Duración de la sesión, en segundos.

> **Importante**
> Un agente entra y sale de cada canal a lo largo del día, así que una jornada normal produce varias sesiones y no una sola. Para calcular las horas conectadas de un día, suma las `duration` de todas sus sesiones en lugar de restar el primer `login_time` del último `logout_time`.

## Pausas de los agentes

`GET /v1/agent/pause` devuelve el detalle de las pausas que tomó un agente, incluida la que esté en curso en el momento de la consulta. Recibe los mismos parámetros que el endpoint de sesiones. Los tipos de pausa se configuran como explica [Pausas del agente](https://docs.audara.io/pausas-agente/).

- **agent_number, agent_name, extension**: Identificación del agente.
- **group_name y queue_name**: Grupo y campaña durante la pausa.
- **pause_name**: Nombre del tipo de pausa, por ejemplo Almuerzo o Capacitación.
- **pause_abbreviation y pause_color**: La abreviatura y el color con los que ese tipo de pausa se muestra en los tableros.
- **start_time**: Momento en que empezó la pausa, en UTC.
- **end_time**: Momento en que terminó. Llega en `null` si la pausa sigue activa.
- **pause_duration**: Duración de la pausa, en segundos. Llega en `null` si la pausa sigue activa.
- **pause_time**: Tiempo permitido para ese tipo de pausa, **en minutos**. Es un valor de configuración, no algo que ocurrió.
- **alarm_duration**: Segundos en los que la pausa **excedió** el tiempo permitido. Viene en 0 cuando el agente no se pasó.
- **agent_level**: Nivel del agente.
- **action y action_user**: Quién cerró la pausa. `action` indica el origen y `action_user` trae el nombre de la persona.

> **Importante**
> Ojo con `alarm_duration`, porque el nombre engaña: no es el umbral configurado sino el exceso ya consumado. Un registro con `alarm_duration` en 0 es una pausa que se cumplió bien, y uno en 300 es una pausa que se pasó cinco minutos. Si lo lees como un umbral, tu informe de adherencia sale al revés.

Para saber si un agente está en pausa ahora mismo, busca el registro cuyos `end_time` y `pause_duration` vengan los dos en `null`.

```
`{
  "data": [
    {
      "agent_number": 5628,
      "agent_name": "Carlos Ramírez",
      "queue_name": "Cobranzas",
      "pause_name": "Almuerzo",
      "pause_abbreviation": "ALM",
      "pause_color": "#FFA500",
      "start_time": "2026-08-15T12:00:10.000Z",
      "end_time": "2026-08-15T12:45:38.000Z",
      "pause_duration": 2728,
      "pause_time": 45,
      "alarm_duration": 28,
      "action": "AGENT",
      "action_user": "Carlos Ramírez"
    }
  ],
  "pagination": { "page": 1, "limit": 50, "has_more": false }
}`
```

## Monitorear el servicio

Dos endpoints te dicen si la API está disponible. No piden autenticación, así que los puedes usar desde tu tablero de monitoreo.

- **GET /live**: Responde `200` con `{"status": "ok"}` si el servicio está en ejecución. No comprueba nada más.
- **GET /ready**: Comprueba además que las dependencias del servicio respondan. Devuelve `200` cuando todo está bien y `503` cuando algo falla.

```
`{
  "status": "ok",
  "checks": {
    "valkey": "ok",
    "mongo_admin": "ok"
  },
  "timestamp": "2026-08-15T10:30:00.000Z"
}`
```

Cuando alguna dependencia falla, el campo `status` pasa a `degraded`, el chequeo correspondiente pasa a `error` y la respuesta llega con código `503`. Monitorea el código HTTP, que es la señal más simple y la que entienden los balanceadores.

## Seguridad

Vale la pena que sepas qué controles hay del otro lado, porque varios explican errores que podrías ver.

- **Solo HTTPS**: Todo el tráfico va cifrado y no se aceptan conexiones en texto plano.
- **Lista de IPs autorizadas**: Cada organización define desde qué direcciones se puede consultar. Las demás reciben un `403`.
- **Tokens sin guardar en claro**: Audara no almacena tu token tal cual, sino su huella. Por eso soporte no te lo puede recordar: si lo pierdes, se emite uno nuevo.
- **Registro de auditoría**: Cada petición queda registrada con la organización, la huella del token, la IP, la ruta y el resultado. Sirve para investigar un uso indebido.
- **Solo lectura**: La API únicamente responde a GET, así que un token filtrado no puede alterar tu operación, aunque sí leerla.

> **Buenas prácticas**
> Ten en cuenta que varias respuestas traen nombres de personas, números de teléfono de tus clientes y, en las pausas, el nombre de quien la cerró. Son datos personales: guárdalos con el mismo cuidado con el que tratas tu base de clientes y no los publiques en un tablero abierto.

## Cuándo escribir a soporte

Contacta al equipo de soporte de Audara para activar tu acceso, emitir o revocar un token, cambiar la lista de IPs autorizadas, subir tus límites de uso o reportar una falla.

Si vas a reportar un problema, incluye el endpoint que usaste, los parámetros que enviaste sin el token, la respuesta que recibiste y la fecha y hora del error. Con eso se resuelve mucho más rápido.
