📡 REST API
REST API предназначен для интеграции ваших систем с платформой Fixorix по HTTPS.
Публичное API устроено как шлюз: он принимает ваш запрос, проверяет API-ключ и его права, сам подставляет идентификатор проекта и передаёт запрос во внутренний сервис Fixorix, возвращая ответ без изменений.
Базовый адрес: https://api.fixorix.ru
Версии: сейчас доступна только v1 — все публичные пути начинаются с /v1/.
Чтобы с проектом работал ИИ-ассистент — Claude Code, Cursor, VS Code, Codex, — подключите его к Fixorix MCP тем же ключом API с включённым «Доступом через MCP». Писать код не нужно.
Обращение к неизвестному пути или к неподдерживаемому методу возвращает 404 Not Found — даже раньше, чем проверяется ключ.
🔎 Где смотреть актуальную спецификацию
👉 Swagger UI: https://api.fixorix.ru/swagger-ui
Открыть его можно и прямо из интерфейса: Настройки проекта → вкладка «API» → кнопка «Swagger UI» (справа вверху, рядом с «Создать ключ»).
Что важно знать про эту спецификацию:
- Она собирается на лету из спецификаций внутренних сервисов, но содержит только опубликованные операции — то, что реально доступно по API-ключу.
- В описании каждой операции есть блок обязательных прав (Required scopes).
- Разделы названы по группам методов. У ботов, пользователей, сообщений и базы знаний к названию добавлен префикс: Bots: …, Users: …, Messages: …, Knowledge Base: …. Остальные разделы идут под своими названиями (Flow, Execution, Trigger, Dashboards, Chats, Tags и т. д.). Первый раздел — Ping. В разделе Widgets собраны и виджеты дашбордов аналитики (
/v1/metrics/widgets/…), и виджет для сайта (/v1/widget/…). - Параметр
projectIdв спецификации скрыт: проект всегда берётся из вашего ключа, см. Проект берётся из ключа. - Авторизация показана как Bearer-ключ, поэтому в Swagger UI работает «Try it out» с вашим собственным ключом.
- Спецификация кэшируется около 5 минут — только что изменившийся набор операций появится в ней с небольшой задержкой.
- Сама спецификация в формате OpenAPI 3.1 (JSON) доступна по адресу
https://api.fixorix.ru/v3/api-docs— её можно скачать для генерации клиента.
Набор публичных маршрутов расширяется, и Swagger UI — единственный источник, который всегда ему соответствует. Эта страница описывает общие правила: ключи, права, лимиты, формат ошибок и параметры запросов.
📦 Что покрывает API
Сейчас наружу опубликовано больше 200 маршрутов и 48 прав доступа (scopes). Маршруты разложены по разделам:
| Раздел | Префикс путей | Группа прав |
|---|---|---|
| Боты и каналы | /v1/bots/… | BOTS_* |
| Участники и проект: роли, группы, приглашения, персоны (клиенты), профиль проекта, чтение настроек проекта | /v1/person-profile/… | USERS_* |
| Сообщения | /v1/messages/…, /v1/message/… | MESSAGES_* |
| База знаний | /v1/knowledge-base/… | KNOWLEDGE_BASE_* |
AI: классификация и метки, извлечение данных, генерация текста и структурированного ответа, модерация, улучшение промпта, ответ по базе знаний (RAG), выбор варианта, саммари, перевод (в т. ч. пакетный), запись в векторное хранилище. Все методы — POST | /v1/ai/… | AI_WRITE |
| Сценарии и их запуски | /v1/flows/…, /v1/flow/executions/…, /v1/flow/triggers/… | FLOWS_* |
| Метрики и дашборды | /v1/metrics/… | METRICS_* |
| Настройки проекта — только чтение | /v1/settings | SETTINGS_READ |
| Хранилище файлов | /v1/storage/… | STORAGE_* |
| Теги | /v1/tags/… | TAGS_* |
| Обращения (техподдержка): списки, статус, приоритет, линия, история и сообщения; шаблоны ответов; AI-подсказки | /v1/tech-support/… | TECH_SUPPORT_* |
Виджет для сайта: виджеты проекта (список, создание, правка, удаление), его вид и тексты (/settings: чтение и замена — PATCH заменяет все поля, welcomeMessage: null убирает приветствие), домены сайта (список; POST находит домен или создаёт его) и HMAC-секреты (список, выпуск нового — rotate, отзыв) | /v1/widget/…, /v1/widget-domains | WIDGETS_* |
| Служебное | /v1/ping | не проверяются |
Таблица показывает разделы и группы прав, а не полные адреса методов. Какие именно операции опубликованы в каждом разделе и какие права требует конкретный метод — написано в Swagger UI, в описании операции (блок Required scopes). Соответствие раздела и группы прав — по названию.
Среди опубликованных разделов нет тикетов: создавать, читать и менять тикеты по API-ключу нельзя. Тикеты ведутся в интерфейсе — см. Система тикетов.
🔐 API-ключи
Экран «API-ключи»
API-ключи создаются и управляются в интерфейсе Fixorix: Настройки проекта → вкладка «API». Заголовок экрана — «API-ключи», подпись — «Управление ключами Public API проекта».
На экране — таблица ключей:
| Колонка | Что показывает |
|---|---|
| Имя | Имя ключа и его описание. У ключа с доступом через MCP — бейдж «MCP: чтение» или «MCP: запись» |
| Права | Коды выданных прав, например BOTS_READ |
| Статус | «Активен», «Отозван» или «Истёк» |
| Автор | Участник, создавший ключ |
| Создан | Дата и время создания |
| Использован | Время последнего вызова, дошедшего до внутреннего сервиса (включая /v1/ping), или «Никогда». Обновляется с задержкой до ~10 секунд |
| Истекает | Дата окончания или «Бессрочный» |
| Действия | Редактирование и отзыв ключа |
Список можно сортировать по колонкам «Имя» и «Создан». Если ключей ещё нет, экран показывает «Пока нет API-ключей».
Создавать, просматривать, изменять и отзывать ключи может только участник с ролью «Администратор» или «Владелец». Вкладка «API» и кнопки на ней видны всем участникам проекта. При нехватке прав над пустым списком появится сообщение «Не удалось загрузить ключи. Возможно, недостаточно прав — нужна роль администратора проекта.», а попытка создать ключ закончится ошибкой «Не удалось создать ключ».
📷 Скриншот: экран «API-ключи» с таблицей ключей и кнопками «Создать ключ» и «Swagger UI» (будет добавлен).
Как создать ключ
- Откройте проект → Настройки → вкладка «API».
- Нажмите «Создать ключ» — откроется окно «Создание API-ключа».
- Заполните поля и отметьте нужные права.
- Нажмите «Создать ключ» в окне.
- Скопируйте секрет из окна «Ключ создан».
Поля окна:
| Поле | Обязательно | Описание |
|---|---|---|
| Имя | да | Понятное название, например ci-pipeline-key, до 255 символов |
| Описание | нет | Свободный комментарий |
| Срок действия | нет | Дата: ключ действует до конца выбранного дня (23:59:59 по вашему времени). Подсказка — «Оставьте пустым для бессрочного ключа» |
| Права доступа (scopes) | да | Матрица «ресурс × действие». Нужно отметить хотя бы один пункт |
| «Для ИИ-клиента (MCP)» | нет | Переключатель: ключ сможет работать через Fixorix MCP. Открывает выбор пресета прав и режима «Доступ через MCP», см. Ключи и права для MCP. Выключен — ключ работает только с REST API |
Кнопка «Создать ключ» станет активной, когда заполнено имя и отмечено хотя бы одно право. Если сервер отклонит данные (слишком длинное имя, дата срока в прошлом), форма покажет «Не удалось создать ключ».
Про выбор прав подробно — на странице Scopes.
Секрет ключа
Секрет выглядит как fxr_ и 43 случайных символа, например fxr_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX.
В окне «Ключ создан» есть кнопка «Копировать» и предупреждение: «Скопируйте секрет сейчас — он показывается единственный раз и больше не будет доступен.»
На сервере хранится только необратимый хеш секрета. Восстановить потерянный секрет невозможно — придётся создать новый ключ и отозвать старый.
Редактирование и отзыв ключа
- Редактирование — кнопка в строке таблицы, окно «Редактирование API-ключа», кнопка «Сохранить». Изменить можно имя и описание — в том числе у отозванного ключа — и режим «Доступ через MCP»: «Без MCP», «Только чтение» или «Чтение и запись». Кнопка «Сохранить» неактивна при пустом имени; если ничего не изменилось, окно просто закроется.
- Отзыв — кнопка в строке таблицы, окно «Отзыв ключа»: вопрос «Вы уверены, что хотите отозвать ключ?», имя ключа, число выданных прав и предупреждение «После отзыва ключ перестанет работать. Действие необратимо.», кнопка «Отозвать». После отзыва появится «Ключ отозван», окно закроется само. Отозванный ключ остаётся в списке со статусом «Отозван», повторно отозвать его нельзя.
Правила безопасности
- Ключ привязан к одному проекту — запросы выполняются в его контексте.
- Храните секрет как пароль: в переменных окружения или хранилище секретов.
- Не используйте ключ в клиентских приложениях (frontend, мобильные приложения).
- Выдавайте минимально необходимые права.
- Периодически проверяйте колонку «Использован»: ключи, которые давно не вызывались, стоит отозвать.
Ограничения
| Ограничение | Что это значит на практике |
|---|---|
| Права выпущенного ключа не меняются | Чтобы добавить или убрать право, ключ нужно отозвать и выпустить новый — новый секрет придётся прописать во всех интеграциях |
| Срок действия не меняется | Продлить ключ нельзя; заранее следите за колонкой «Истекает» и выпускайте новый до этой даты |
| Ротации секрета нет | Операции «перевыпустить секрет, сохранив ключ» не существует. Смена секрета — это всегда новый ключ и отзыв старого |
| Лимит запросов одинаков для всех | 1000 запросов в минуту на ключ; настроить лимит под конкретный ключ, интеграцию или тариф нельзя |
| Один ключ — один проект | Ключ работает только в том проекте, где выпущен. Для второго проекта нужен свой ключ |
Заводите отдельный ключ на каждую интеграцию и каждое окружение. Тогда смена набора прав или компрометация одного ключа не заставит переключать все остальные.
🩺 Проверка ключа
Прежде чем отлаживать интеграцию, убедитесь, что ключ живой и шлюз отвечает:
curl -i -X GET \
-H "Authorization: Bearer <YOUR_API_KEY>" \
https://api.fixorix.ru/v1/ping
- Успешный ответ —
200с пустым телом и заголовкомX-Request-Id(вашим, если вы его передали, или сгенерированным шлюзом). - Права (scopes) для
pingне проверяются — важна только валидность самого ключа. - Вызов обновляет отметку «Использован» у ключа и расходует одну единицу лимита запросов.
Что знает о себе ключ: GET /v1/key
Метод описывает сам ключ, которым вызван: проект, права, срок и режим «Доступ через MCP». Удобно, чтобы проверить, какой ключ стоит в интеграции, не открывая дашборд.
curl -s -X GET \
-H "Authorization: Bearer <YOUR_API_KEY>" \
https://api.fixorix.ru/v1/key
{
"keyId": "0b8e7c1a-…",
"projectId": "5a1f3d2e-…",
"name": "Cursor — Иван",
"scopes": ["FLOWS_READ", "KNOWLEDGE_BASE_READ", "TECH_SUPPORT_READ"],
"expiresAt": null,
"mcpAccess": "READ_ONLY",
"rateLimitPerMinute": 1000
}
| Поле | Что значит |
|---|---|
keyId, projectId | Идентификаторы ключа и его проекта |
name | Имя ключа |
scopes | Выданные права, по алфавиту |
expiresAt | Когда истекает; null — бессрочный ключ |
mcpAccess | Режим «Доступ через MCP»: NONE, READ_ONLY или READ_WRITE, см. Fixorix MCP |
rateLimitPerMinute | Лимит запросов ключа в минуту |
Как и /v1/ping, метод не требует прав и не обращается к внутренним сервисам, но расходует единицу лимита. Секрет и автор ключа в ответе не возвращаются. Неизвестный, отозванный, истёкший ключ и ключ без прав получают 401.
✅ Как делать запросы
Заголовки
| Заголовок | Назначение |
|---|---|
Authorization: Bearer <YOUR_API_KEY> | Обязателен для всех запросов, включая /v1/ping |
Accept: application/json | Ожидаемый формат ответа |
Content-Type: application/json | Для методов с телом запроса |
X-Request-Id: <ваш идентификатор> | Рекомендуется. Если не передать, шлюз сгенерирует свой, но вернёт его только в ответах /v1/ping, /v1/key и в ошибках самого шлюза. Передавайте свой идентификатор и называйте его при обращении в поддержку |
Во внутренние сервисы уходят только заголовки Accept, Accept-Language, Content-Type, X-Request-Id и Idempotency-Key. Остальные — в том числе ваши Authorization, Host, cookie и X-Forwarded-* — шлюз отбрасывает и подставляет служебные.
Пример запроса
curl -X GET \
-H "Authorization: Bearer <YOUR_API_KEY>" \
-H "Accept: application/json" \
https://api.fixorix.ru/v1/ping
Остальные вызовы устроены так же — меняются путь, метод и тело. Точные адреса берите в Swagger UI: там же запрос можно выполнить кнопкой «Try it out» и увидеть готовую команду curl.
Проект берётся из ключа
Ключ привязан к одному проекту, и все запросы по нему выполняются только в этом проекте:
projectIdпередавать не нужно. ПараметрprojectIdв строке запроса шлюз отбрасывает всегда. Методам, которым внутренний сервис нужен проект в строке запроса, шлюз сам добавляет проект ключа, а если метод принимаетprojectIdв теле JSON — перезаписывает это поле. Тело такого метода должно быть JSON-объектом, иначе шлюз ответит400.- Объект другого проекта недоступен. Запрос к чату, документу, боту или другому объекту чужого проекта по его идентификатору завершается ошибкой (
403или404— зависит от сервиса), данные не возвращаются. - Ключ действует с правами не выше администратора проекта. Методы, которым нужна роль владельца (удаление проекта, создание и удаление настроек), по ключу недоступны.
📄 Параметры, пагинация и сортировка
Точный набор параметров каждого метода смотрите в Swagger UI. Общие правила такие:
| Параметр | По умолчанию | Что делает |
|---|---|---|
page | 0 | Номер страницы, нумерация с нуля |
size | 20 | Размер страницы у постраничных методов |
sort | зависит от метода | Поле и направление, например sort=createdAt,desc |
- Постраничные не все методы: часть возвращает полный список и параметров страницы не принимает.
- Список запусков сценариев (
GET /v1/flow/executions) постраничных параметров не принимает: число записей задаётсяlimit(по умолчанию 200, максимум 1000). - У поиска по базе знаний порядок результатов фиксированный — от новых документов к старым, задать сортировку нельзя.
⏱ Лимиты запросов
- 1000 запросов в минуту на каждый API-ключ. Лимит считается по ключу, а не по проекту: у двух ключей одного проекта — по 1000 запросов в минуту каждый.
- Окно — календарная минута: счётчик обнуляется в начале следующей минуты.
- При превышении возвращается
429 Too Many Requestsс теломRate limit exceededи заголовками:Retry-After: <секунд>— сколько секунд осталось до начала следующей минуты;X-RateLimit-Limit: <лимит>— действующий лимит.
1000 запросов в минуту — единое значение для всех ключей и всех проектов. Поднять его для отдельного ключа, интеграции или тарифа нельзя.
При недоступности подсистемы лимитов запросы пропускаются без подсчёта — на клиенте это никак не проявляется.
❗ Формат ошибок
Ошибки самого шлюза возвращаются обычным текстом (не JSON): корректный HTTP-статус и одна строка с описанием.
| Статус | Тело ответа | Когда возникает |
|---|---|---|
401 | Missing or invalid Authorization header | Нет заголовка Authorization или он не начинается ровно с Bearer (с заглавной B и одним пробелом) |
401 | Invalid API key | Такого ключа не существует |
401 | API key is not active | Ключ отозван |
401 | API key has expired | Истёк срок действия ключа |
401 | API key has no scopes | У ключа не выдано ни одного права |
403 | Insufficient scopes for this operation | Ключу не хватает прав для этого метода |
404 | Not Found | Неизвестный путь или метод |
429 | Rate limit exceeded | Превышен лимит запросов |
502 | Bad Gateway | Шлюз не смог соединиться с внутренним сервисом |
504 | Gateway Timeout | Внутренний сервис не ответил за 30 секунд |
Ошибки внутренних сервисов (400, 403, 404, 409, 422, 500 и т. д.) проксируются клиенту как есть — их формат определяет соответствующий сервис Fixorix. Например, ошибки валидации тела запроса приходят именно оттуда: сам шлюз тело не проверяет.
Ошибки шлюза в JSON
Если интеграции удобнее разбирать JSON, передайте заголовок Accept: application/problem+json. Тогда ошибки самого шлюза приходят так:
{
"error": {
"code": "INSUFFICIENT_SCOPE",
"message": "Insufficient scopes for this operation",
"requiredScopes": ["BOTS_READ"]
},
"requestId": "6f1c2b9a-…"
}
| Статус | error.code |
|---|---|
400 | BAD_REQUEST, VALIDATION_ERROR |
401 | INVALID_API_KEY (в том числе ключ без прав), KEY_REVOKED, KEY_EXPIRED |
403 | INSUFFICIENT_SCOPE — с полем requiredScopes: каких прав требует метод |
404 | ROUTE_NOT_FOUND |
429 | RATE_LIMITED |
502, 504 | BAD_GATEWAY, GATEWAY_TIMEOUT |
500 | INTERNAL_ERROR |
Без этого заголовка ошибки остаются текстовыми, как в таблице выше. Ошибки внутренних сервисов заголовок не меняет.
Передавайте в каждом запросе свой X-Request-Id (например, UUID) и сохраняйте его в логах интеграции: шлюз возвращает этот заголовок только в ответах /v1/ping, /v1/key и в своих ошибках. По нему поддержка найдёт запрос в логах.
Порядок проверок
Шлюз проверяет запрос в такой последовательности:
- Подбирает маршрут по методу и пути — если маршрута нет, сразу
404(ещё до проверки ключа). - Читает
Authorization: Bearer …— иначе401. - Находит ключ по секрету — иначе
401. - Проверяет, что ключ активен, не истёк и у него есть хотя бы одно право — иначе
401. - Проверяет права, требуемые маршрутом — иначе
403. - Проверяет лимит запросов — иначе
429. - Передаёт запрос во внутренний сервис и возвращает его ответ.
Поэтому запрос с неверным ключом на несуществующий путь вернёт 404, а не 401.
🧪 Диагностика частых случаев
| Симптом | Причина и решение |
|---|---|
404 Not Found на, казалось бы, существующий метод | Публично опубликован ограниченный список маршрутов, всё остальное отдаёт 404. Сверьте путь и HTTP-метод со Swagger UI |
401 Unauthorized | Проверьте заголовок Authorization: Bearer <ключ> — секрет начинается с fxr_. Посмотрите статус ключа на экране «API-ключи»: «Отозван» и «Истёк» дают 401. Ключ без единого выданного права тоже даёт 401 |
403 Forbidden | Ключу не хватает прав для этого метода. Требуемые права указаны в описании операции в Swagger UI (блок Required scopes). Изменить права у существующего ключа нельзя — выпустите новый и отзовите старый |
429 Too Many Requests | Используйте заголовок Retry-After и повторяйте запрос с задержкой. Если лимита систематически не хватает, распределите нагрузку между несколькими ключами — лимит считается на ключ |
502 или 504 | Проблема на стороне Fixorix: шлюз не достучался до внутреннего сервиса или тот не ответил за 30 секунд. Повторите запрос позже; при повторении сообщите в поддержку значение X-Request-Id, которое вы передали в запросе |
Кто что может
| Действие | Минимальная роль |
|---|---|
| Открыть вкладку «API» | Участник проекта |
| Посмотреть список ключей | Администратор |
| Создать ключ | Администратор |
| Изменить имя и описание ключа | Администратор |
| Отозвать ключ | Администратор |
| Включить или выключить у ключа «Доступ через MCP» | Администратор |
| Вызывать методы API по выпущенному ключу | Роль не проверяется — важны только права самого ключа |
Если запрос стабильно возвращает 502, 504 или неожиданный ответ, напишите в поддержку и приложите значение X-Request-Id, которое вы передали в запросе, — по нему запрос находится в логах.
Scopes · База знаний в API · Сценарии в API · Webhooks · Fixorix MCP · API Fixorix