Перейти до вмісту

Публічний API

Публічний API Aelo — це API аналітики дзвінків (call analytics API, conversation intelligence API): ви надсилаєте записи дзвінків або чатів із ваших власних систем — CRM, платформи телефонії, кастомного пайплайна — і забираєте записи та їх аналіз (оцінки, резюме, заперечення) після завершення обробки. API прив’язаний до організації: кожен запит діє від імені організації, яка видала ключ, і кожна відповідь обмежена даними цієї організації.

Доступний на тарифах Starter і вище. Організації на безкоштовному тарифі не можуть ні видавати, ні використовувати публічні API-ключі.

  1. Перейдіть у Налаштування → API ключі. Цей розділ бачить лише власник організації (роль client) — адміністратори, супервайзери й агенти не можуть керувати ключами.
  2. Оберіть назву, позначте один або обидва скоупи (records:write, records:read) і за потреби вкажіть дату завершення дії.
  3. Ключ у відкритому вигляді (aelo_sk_…) показується один раз, у момент створення. Збережіть його самостійно — Aelo зберігає лише його хеш і не зможе показати його повторно. Якщо ключ втрачено, відкличте його і видайте новий.

Організація може мати не більше 10 активних ключів одночасно — відкликайте невикористані, перш ніж видавати нові.

Кожен запит передає ключ як bearer-токен:

Authorization: Bearer aelo_sk_YOUR_KEY

Усі ендпоінти знаходяться під https://api.aelo.cloud/api/public/v1.

Ключ відкриває доступ лише до того, що дозволяють його скоупи:

СкоупДає доступ до
records:writeСтворення записів (POST /records, POST /records/upload)
records:readСписок і читання записів та аналізів (три маршрути GET)

Запит до ендпоінта, який не покривають скоупи ключа, завершиться помилкою insufficient_scope, навіть якщо сам ключ дійсний.

ЛімітЗначення
Запитів на ключ200 / хвилину
Розмір multipart-завантаження (POST /records/upload)25 МБ
Розмір файлу за fileUrl (POST /records)100 МБ, або 25 МБ, якщо джерело не повідомляє Content-Length
Тайм-аут завантаження за fileUrl30 секунд
Активних API-ключів на організацію10
Розмір сторінки списку записів50 за замовчуванням, максимум 100 (limit понад 100 мовчки зменшується, а не відхиляється)

Ліміт для multipart нижчий за ліміт для fileUrl, бо multipart-тіло потрібно повністю буферизувати в пам’яті перш ніж Aelo зможе його прочитати, а завантаження за fileUrl йде потоком напряму у сховище — за умови, що джерело повідомляє свій Content-Length. Джерело, яке його не повідомляє, потоком передати не можна: воно буферизується в пам’яті, як multipart-тіло, і обмежене тими самими 25 МБ. Якщо ваш аудіофайл більший за 25 МБ, завантажте його у сховище, до якого маєте доступ, і передайте fileUrl замість самого файлу — обидва варіанти детально розібрані у Завантаженні дзвінків і чатів.

Метод і шляхСкоупЩо робить
POST /recordsrecords:writeСтворює запис із fileUrl (дзвінки) або textContent (чати)
POST /records/uploadrecords:writeСтворює запис дзвінка із завантаженого аудіофайлу (multipart)
GET /recordsrecords:readСписок записів вашої організації
GET /records/{recordId}records:readОтримати один запис
GET /records/{recordId}/analysisrecords:readОтримати останній аналіз запису

Обидва ендпоінти завантаження, їхні поля запиту, поведінка ідемпотентності та попередження, які вони повертають, розібрані у Завантаженні дзвінків і чатів. Решта описана нижче.

Повертає записи від найновіших до найстаріших. Архівні записи виключені — і ніяк не позначені: у відповіді немає поля archived, тож архівний запис просто не з’являється у списку.

Параметри запиту:

ПараметрЗа замовчуваннямПримітка
limit50Обмежений зверху значенням 100
offset0
createdAfterISO-8601. Включно (createdAt >= createdAfter)
createdBeforeISO-8601. Включно (createdAt <= createdBefore)
{
"data": [
{
"id": "rec_...",
"projectId": "your-project-id",
"type": "call",
"status": "completed",
"externalId": "crm-call-12345",
"createdAt": "2026-07-01T10:00:00.000Z",
"occurredAt": "2026-07-01T09:58:12.000Z",
"durationSeconds": 184,
"agentId": "42",
"agentName": "Ivan Petrov",
"callDirection": "outbound"
}
],
"pagination": { "limit": 50, "offset": 0, "total": 1 }
}

Повертає один запис у тому самому форматі, що й список. Відповідає record_not_found (404), якщо id не існує або належить іншій організації — ці два випадки навмисно невідрізнювані.

Повертає останній аналіз запису.

{
"recordId": "rec_...",
"analysisId": "an_...",
"createdAt": "2026-07-01T10:04:30.000Z",
"summary": "Customer asked about pricing tiers; agent...",
"qualityScore": 78,
"metrics": {
"greetingScore": 90,
"needsScore": 70,
"clarityScore": 80,
"objectionScore": 65,
"closingScore": 75,
"politenessScore": 95,
"saleProbability": 62
}
}

qualityScore — це канонічна оцінка: те саме число, що показує ваш дашборд для цього дзвінка, а не самооцінка моделі. Кожна метрика дорівнює null, якщо аналіз не дав по ній значення (безоцінна категорія дзвінка або пункт рубрики, вимкнений у вашому проєкті) — ніколи не 0 замість «не оцінено». saleProbability стосується лише дзвінків; для чатів воно завжди null.

Відповідь навмисно вужча за те, що Aelo зберігає всередині: провайдер, модель, профіль промпту, кількість токенів і вартість не входять у публічний контракт.

Дві ситуації, що виглядають як 404, розрізняються кодом помилки, бо подальша дія відрізняється:

  • record_not_found — не існує сам id запису (або він не ваш). Виправте id.
  • analysis_not_found — запис існує, але аналізу в нього немає. details.analysisExpected каже, чи він ще буде: true — продовжуйте опитувати, false — запис завершився без аналізу і ніколи його не матиме, опитування час припинити. Частина дзвінків закінчується так за задумом: надто короткий для оцінювання дзвінок (details.reason: "short_call") або запис, що впав у пайплайні ("record_failed"). details.recordStatus у будь-якому разі повідомляє поточний статус запису.

Будь-яка помилка повертається в одному форматі:

{
"error": {
"code": "invalid_request",
"message": "Human-readable description.",
"details": { "field": "..." }
}
}

details необов’язкове і, якщо присутнє, описує лише ваш власний запит — ніколи внутрішній стан. Нерозпізнане поле в JSON-тілі, формі чи рядку запиту відповідає invalid_request і називає кожне проблемне поле, а також підказку didYouMean, якщо знайдено близький збіг зі справжнім ім’ям (наприклад, projectIDprojectId).

КодСтатусЗначення
invalid_api_key401Відсутній/некоректний заголовок Authorization, або ключ невідомий, відкликаний чи прострочений (усі три випадки виглядають однаково — навмисно)
insufficient_scope403У ключа немає скоупу, потрібного цьому ендпоінту
tier_not_eligible403Організація на безкоштовному тарифі
feature_disabled403Адміністратор вашої організації вимкнув публічний API. Ключ залишається дійсним, зміна тарифу не допоможе — попросіть увімкнути назад
insufficient_balance402Включені в тариф хвилини за цей цикл вичерпані, а баланс кредитів порожній. Запис не створено — поповніть баланс у «Налаштування → Білінг» і надішліть запит ще раз
project_not_found404projectId не існує або належить іншій організації
project_not_accepting_records409Проєкт існує, але його статус paused або archived — адміністратор організації має знову активувати його, перш ніж проєкт зможе приймати записи
record_not_found404Id запису не існує або належить іншій організації
analysis_not_found404Запис існує, але аналізу немає — опитуйте, поки details.analysisExpected = true, і припиніть, коли false
not_found404Такого маршруту під /api/public/v1 не існує
rate_limited429Понад 200 запитів за хвилину на цей ключ
payload_too_large413Див. Ліміти вище
unsupported_media_type415Завантажений/скачаний контент — не аудіо і не відео
invalid_request400Тіло запиту, форма або рядок запиту не пройшли валідацію
fetch_failed400Не вдалося скачати файл за fileUrl
resolution_unavailable503Aelo зараз не змогла перевірити адресу призначення fileUrl — тимчасово, повторіть (заголовок Retry-After)
service_unavailable503Сховище аналізів тимчасово недоступне — тимчасово, повторіть (заголовок Retry-After)
internal_error500Непередбачений збій на боці сервера

Відповідь 503 завжди містить заголовок Retry-After (у секундах) — не вважайте це остаточною відмовою, повторіть запит через цей час.

Aelo — це API аналітики дзвінків?

Section titled “Aelo — це API аналітики дзвінків?”

Так. Публічний API Aelo — REST API аналітики дзвінків (call analytics API) на https://api.aelo.cloud/api/public/v1: Bearer-ключі організації (aelo_sk_…), скоупи records:write / records:read, 200 запитів на хвилину на ключ. Доступний на тарифах Starter і вище.

Як завантажити записи дзвінків на аналіз?

Section titled “Як завантажити записи дзвінків на аналіз?”

Два способи: POST /records/upload приймає сам аудіофайл (multipart, до 25 МБ); POST /records приймає fileUrl, звідки Aelo завантажить запис (до 100 МБ). Чати надсилаються через POST /records як textContent. Повторні надсилання дедуплікуються за externalId: передайте свій ідентифікатор, і повторний запит поверне вихідний запис, а не створить другий. Обидва ендпоінти описані в розділі Завантаження дзвінків і чатів.

Bitrix24 він зазвичай не потрібен: нативна інтеграція аналізує дзвінки взагалі без коду. Публічний API — для всього іншого: власної телефонії, дата-пайплайна або CRM, з якою в Aelo поки немає інтеграції.

  • Завантаження дзвінків і чатів — поля запиту, ліміти розміру, ідемпотентність і попередження для обох ендпоінтів завантаження
  • Ціни — публічний API входить у тарифи Starter і вище