# Изменения API: 29 сентября 2026

[← Журнал изменений](/docs/changelog) · [Сентябрь 2026](/docs/changelog/2026-09)

### NEW-0929-1: Справочники единиц измерения и ставок НДС каталога

Через API Вайбкод доступны `GET`, `POST`, `PATCH` и `DELETE` для `/v1/catalog-measures` и `/v1/catalog-vat-rates`. Перед созданием товара можно получить допустимые значения `measure` и `vatId`; для обеих сущностей доступны также поиск, поля и batch.

### BC-0929-2: сортировка сотрудников и реквизитов применяет порядок по идентификатору

> Поддержка старого формата до: не предусмотрена

**Было**

`sort=-id` и `order[id]=desc` не меняли порядок сотрудников, реквизитов и шаблонов реквизитов. Сортировка сотрудников по другому обычному полю могла быть молча проигнорирована, а запрос возвращал HTTP 200 со строками.

**Стало**

Обе формы сортируют эти списки по `id` по убыванию на одиночных эндпоинтах, в поиске и в `POST /v1/batch`. У сотрудников `id` — единственное поддержанное обычное поле сортировки. Другие обычные поля отклоняются с `UNKNOWN_SORT_FIELD`. `UF_*` сохраняет прежний passthrough на одной странице, а при многостраничной выдаче отклоняется с `INVALID_SORT_FIELD`. Ответы на поддержанные запросы остаются HTTP 200.

**Что делать интеграторам**

Запросы сортировки по `id` менять не нужно. Для сотрудников не используйте другие обычные поля. `UF_*` оставляйте только в одностраничных запросах и учитывайте, что порядок по нему зависит от Битрикс24.

**Затронутые эндпоинты:** [GET /v1/users](/docs/entities/users/list), [POST /v1/users/search](/docs/entities/users/search), [GET /v1/requisites](/docs/entities/requisites/list), [POST /v1/requisites/search](/docs/entities/requisites/search), [GET /v1/requisite-presets](/docs/entities/requisite-presets/list), [POST /v1/requisite-presets/search](/docs/entities/requisite-presets/search), [POST /v1/batch](/docs/batch).

### NEW-0929-5: услуги каталога доступны через V1

В API Вайбкод добавлено семейство `/v1/catalog-services`: список, поиск, чтение, создание, изменение и удаление услуг. Для списка и поиска требуется `filter.iblockId`. Цены услуг задаются через существующий `/v1/catalog-prices`.

### NEW-0929-8: шлюз коннекторов для Коворка

API Вайбкод отвечает на [POST /v1/connectors/mcp](/docs/connectors-mcp) — MCP-шлюз, через который десктоп Коворк вызывает инструменты подключённых сервисов. Шлюз принимает только ключ десктопа Коворк, другой ключ получает `403 CONNECTOR_KEY_NOT_ALLOWED`. Пока функция не включена, путь отвечает `404 ROUTE_NOT_FOUND`.

### FIX-0929-9: превью смены тарифа Коворк/Код называет цену по акции

**Было**

`GET /v1/cowork/subscription/preview` называл в `chargeVibes` и `netVibes` цену тарифа за срок, даже если на эту покупку действовала скидка платформы: покупка затем списывала меньше, чем показало превью.

**Стало**

`chargeVibes` и `netVibes` учитывают скидку, которую получит эта покупка, — ровно ту сумму, что будет списана. На продлении уже оплаченного тарифа и на повторе текущего тарифа скидка не применяется, как и при самой покупке. Форма ответа не меняется, ответ по-прежнему HTTP 200.

### NEW-0929-10: причина и действие в отказах Битрикс24 по правам и скоупу

Ответы `403 BITRIX_ACCESS_DENIED` и `422 BITRIX_ERROR` с `b24Code` `ACCESS_DENIED_EXTEND` или `NO_AUTH_FOUND` несут новые необязательные поля. `error.cause` различает отказ по правам пользователя Битрикс24 (`b24_permission`), нехватку скоупа у учётных данных ключа (`b24_scope`) и неустановимую причину (`unknown`). `error.fix` называет действие (`action`) и место, где оно совершается (`via`). `error.method` — метод Битрикс24, не длиннее 100 символов. `error.requiredScope` — недостающий скоуп, когда он известен. `error.hint` на этих отказах приходит всегда. Значения `cause`, `fix.action` и `fix.via` — открытые наборы: незнакомое значение читайте как `unknown` или `none`. Коды и статусы ответов не изменились. Разбор значений — [Авторизация, ключи и права](/docs/errors/auth#bitrix_access_denied-403).

### FIX-0929-11: отказ по правам на пост отдаёт сообщение на английском

**Было**

[PATCH /v1/posts/{id}](/docs/feed/posts/update), [DELETE /v1/posts/{id}](/docs/feed/posts/delete) и [POST /v1/posts/{id}/share](/docs/feed/posts/share) при отказе Битрикс24 по правам на пост отдавали в `error.message` текст портала как есть — на портале с русским языком это был русский текст.

**Стало**

`error.message` такого отказа — фиксированный английский текст `Bitrix24 denied access to this post.`, в ответе также приходят `error.cause`, `error.method`, `error.fix` и `error.hint`. Код и статус прежние — `403 BITRIX_ACCESS_DENIED`.

**Влияние на интеграторов**

Код клиента, который ветвится по `error.code`, менять не нужно. Разбор текста `error.message` этого отказа больше не требуется.

### BC-0929-12: Поиск файлов и папок проверяет оба указанных идентификатора родительской папки

> Поддержка старого формата до: не предусмотрена

**Было**

В [POST /v1/files/search](/docs/entities/files/search) и [POST /v1/folders/search](/docs/entities/folders/search) идентификатор папки можно было указать и в теле запроса, и в `filter`. Если одно значение было корректным, некорректное значение в другом месте могло попасть в запрос к Диску или остаться незамеченным.

**Стало**

Оба указанных значения должны быть непустыми скалярами. Запрос с объектом, массивом, `null` или пустой строкой в любом из этих мест отклоняется до обращения к Диску. Два корректных значения по-прежнему используют значение верхнего уровня.

**Что делать интеграторам**

Если идентификатор указан в обоих местах, удалите некорректное значение и оставьте корректный `folderId` или `parentId`. Ранее такой запрос мог проходить, когда корректное значение находилось на верхнем уровне.

### BC-0929-14: границы чтения чатов, метаданных файлов и восстановления публикации

> Поддержка старого формата до: не предусмотрена

**Было** Личный ключ `vibe_api_*` в режиме `READONLY` получал `403 WRITE_BLOCKED_READONLY_KEY` на [GET /v1/chats/{dialogId}/load](/docs/chats/messages/load), [GET /v1/chats/{dialogId}/messages?format=v2](/docs/chats/messages/list) и [GET /v1/chats/messages/{messageId}/context](/docs/chats/messages/context).

**Стало** При наличии скоупа `im` и прав пользователя в Битрикс24 эти чтения проходят, ответ успешного чтения остаётся HTTP 200. В чате с разрешённым автовступлением вызов может добавить сотрудника в участники. Битрикс24 обновляет присутствие на этих чтениях. Загрузка чата также может запустить ленивое преобразование проекта. REST-параметров отключения этих эффектов нет. Сами методы не отмечают сообщения прочитанными. Явные команды изменения остаются закрытыми для ключа только для чтения.

**Что делать интеграторам** Личный ключ сотрудника только для чтения может выполнять эти именованные чтения без открытия команд записи. Авторизация гостевой сессии не входит в этот контракт. Форма успешного ответа не меняется.

**Было** [GET /v1/chats/files/{fileId}](/docs/chats/files/file-get) принимал ключ только со скоупом `im` и обращался к файлу Диска по произвольному ID. [PATCH /v1/chats/{dialogId}/messages/{messageId}](/docs/chats/messages/update) и [DELETE /v1/chats/{dialogId}/messages/{messageId}](/docs/chats/messages/delete) сообщения не проверяли соответствие `dialogId` и `messageId`.

**Стало** Для READONLY требуется существующий чат: `chatN` либо числовой собеседник (включая разрешённый `me`), подтверждённый в последних диалогах того же сотрудника. Проверка ограничена 4000 исходными строками; неподтверждённая привязка получает `403 WRITE_BLOCKED_READONLY_KEY` до метода, способного создать чат. Метаданные требуют одновременно `im` и `disk`, а также права пользователя на файл в Битрикс24. Отсутствие любого скоупа даёт `403 SCOPE_DENIED` до обращения к порталу. Изменение сообщения допускается только после нахождения точного ID в доступной истории указанного диалога. Несоответствие даёт `404 MESSAGE_NOT_FOUND_IN_DIALOG`, непригодный полученный ответ проверки — `503 MESSAGE_MEMBERSHIP_UNAVAILABLE`; другие ошибки проверки сохраняют обычный HTTP-статус и код API. Изменение при отказе не отправляется. В [GET /v1/chats/recent](/docs/chats/discovery/recent) смещение отсчитывает видимые уникальные строки. Подтверждение окна ограничено 20 страницами или 4 000 строками, превышение даёт `503 RECENT_WINDOW_UNAVAILABLE` вместо неполного успешного ответа. В ответе метаданных остаются восемь полей: `id`, `name`, `size`, `type`, `detailUrl`, `createdBy`, `createdAt`, `updatedAt`. Прежнее необязательное поле `downloadUrl` удалено из метаданных и успешной загрузки файла, чтобы не передавать URL с учётными данными портала. Успешные HTTP 200 ответы изменения сообщения сохраняются. Загрузка файла в чат по-прежнему требует `im`. В [POST /v1/chats/messages/bulk](/docs/chats/messages/bulk) повтор вычисленного ключа (`id`, иначе `dialogId`) теперь даёт `400 INVALID_PARAMS` до любого вызова портала вместо потери первого элемента. Уникальные строковые ключи, включая имена свойств Object, сохраняются. Курсоры пакета принимают неотрицательные безопасные целые числа и строки десятичных цифр в том же диапазоне; `null` по-прежнему пропускает курсор. Проверка и нормализация выполняются до обращения к порталу. Неполный или противоречивый исход пакета и непригодный ответ опроса событий получают `502 BITRIX_ERROR` вместо ложного HTTP 200. Пустая страница последних диалогов с заявленным продолжением или строка без подтверждённого ID получает `503 RECENT_WINDOW_UNAVAILABLE`; здоровые ответы сохраняют форму.

**Что делать интеграторам** Для ключа только чтения используйте `chatN` существующего чата или личную привязку из последних диалогов; обрабатывайте отказ неподтверждённого контекста. Добавьте `disk` к ключам чтения метаданных. Для байтов вместо `downloadUrl` вызывайте [GET /v1/files/{fileId}/download](/docs/entities/files/download) с `disk` или `crm`; этот запрос использует авторизацию ключа. Передавайте ID диалога, в котором находится изменяемое сообщение. Обрабатывайте отказ проверки принадлежности и не пытайтесь изменить сообщение через другой диалог. Для глубокой навигации последних диалогов используйте режим v2 с курсором, обработайте временный отказ проверки окна. Старый доступ только по `im` закрывается сразу для устранения нарушения границы скоупов.

**Было** После загрузки файла на Диск ошибка публикации в чате не объясняла, сохранился ли файл. Автоматический повтор или удаление после неоднозначного отказа могли создать дубль либо удалить уже прикреплённый файл.

**Стало** [POST /v1/chats/{chatId}/files](/docs/chats/files/upload) не повторяет загрузку и публикацию автоматически. Ошибка после загрузки сохраняет исходные статус и код, дополнительно возвращает `meta.uploadRecovery` с ID файла и чата, результатом проверки публикации и удаления. Удаление допускается только после доказанного отказа до прикрепления и касается файла этого запроса. При неизвестном результате файл сохраняется. Успешный HTTP 201 возвращает `fileId`, `name`, `size`, без прежнего необязательного `downloadUrl`.

**Что делать интеграторам** Проверьте историю чата и метаданные указанного файла перед восстановлением. Не повторяйте загрузку автоматически при неизвестном результате публикации.

**Было** [GET /v1/chats/{chatId}/folder](/docs/chats/files/folder) мог инициализировать отсутствующую папку на Диске под ключом только для чтения.

**Стало** Инициализация требует `READWRITE`; закрывающие режимы получают `403 WRITE_BLOCKED_READONLY_KEY` до обращения к этому методу. Чтение списка файлов, метаданных и содержимого сохраняется.

**Что делать интеграторам** Для получения папки используйте ключ с правом записи. При ошибке публикации после загрузки проверенные локальные отказы до отправки позволяют удалить только файл этого запроса; неизвестные результаты сохраняют файл. Загрузка, публикация и компенсация не повторяются автоматически после 429 либо отказа по скоупам.

**Было** [POST /v1/chats](/docs/chats/management/create) передавал список `users` без местной проверки; некорректные элементы могли дать ошибку Битрикс24 или быть отброшены при создании чата.

**Стало** Перед `im.chat.add` предоставленный список проверяется как массив положительных безопасных целых ID. Числа и канонические строки десятичных цифр без начальных нулей или пробелов нормализуются в числа; некорректная форма получает `400 INVALID_PARAMS` до вызова метода. Отсутствующий список и пустой массив остаются допустимыми. Отказ READONLY на запись по-прежнему предшествует проверке тела. Поля привязки к сущности, включая непрозрачный `entityId` вида `DEAL|1663`, сохраняются.

**Что делать интеграторам** Передавайте корректные ID участников; не рассчитывайте на неявное отбрасывание неправильных значений. При `400 INVALID_PARAMS` исправьте форму списка перед повтором.

### NEW-0929-15: второй адрес покупки в подписочном отказе

Отказы `B24_MARKET_SUBSCRIPTION_REQUIRED` и `B24_MARKET_TRIAL_USED` получили необязательное поле `error.details.secondaryUpgradeUrl` — второй адрес покупки, когда аккаунт Битрикс24 его называет. Поле приходит рядом с `error.details.upgradeUrl`; если второго адреса нет, поля в ответе нет.

### NEW-0929-16: головные товары и вариации каталога доступны через V1

Добавлены `/v1/catalog-skus` и `/v1/catalog-offers`: список, поиск, чтение, создание, изменение и удаление. Для списка и поиска нужен `filter.iblockId` соответствующего каталога. Вариация может быть свободной или связанной с головным товаром через `parentId` при создании.

### NEW-0929-17: Чаты: разделы списка диалогов, общие чаты, изменения с момента, закреп и прочтение чатов

Раздел чатов получил десять эндпоинтов на методах мессенджера v2 Битрикс24. Разделы списка диалогов читаются страницами: [GET /v1/chats/recent/channels](/docs/chats/discovery/recent-channels) отдаёт открытые каналы по курсору `lastMessageId`, [GET /v1/chats/recent/collabs](/docs/chats/discovery/recent-collabs) — чаты коллаб, а [GET /v1/chats/recent/external](/docs/chats/discovery/recent-external) — чаты одного раздела по коду `type`, например чаты задач или встреч календаря, оба по курсору `lastMessageDate` и признаку `hasNextPage`. [GET /v1/chats/shared](/docs/chats/discovery/shared) возвращает чаты, общие с указанным сотрудником, а [GET /v1/chats/sync](/docs/chats/discovery/sync) — изменения чатов, сообщений и закрепов с указанного момента. Чат закрепляется в списке диалогов через [POST /v1/chats/:dialogId/pin](/docs/chats/management/pin), место среди закреплённых задаёт [PUT /v1/chats/:dialogId/pin](/docs/chats/management/pin-sort), закреп снимает [DELETE /v1/chats/:dialogId/pin](/docs/chats/management/unpin). [POST /v1/chats/read-all](/docs/chats/management/read-all) отмечает прочитанными все чаты пользователя, [POST /v1/chats/recent/read](/docs/chats/management/read-section) — чаты одного раздела списка. Лимиты вне диапазона обрезаются с эхом в `meta`, неизвестный или повторный параметр и лишнее поле тела отклоняются с `400 INVALID_PARAMS`. Закреп, порядок закреплённых и прочтение — запись: ключ только для чтения получает на них `403 WRITE_BLOCKED_READONLY_KEY`, как описано на странице [прав доступа](/docs/access-rights).

### FIX-0929-18: Legacy-список чатов снова поддерживает глубокое смещение

[GET /v1/chats/recent](/docs/chats/discovery/recent) без `format=v2` снова передаёт глубокий `OFFSET` в Битрикс24 и читает одну страницу с возможным дозапросом пустой граничной строки, как раньше. Удалены перечитывание префикса, окно 4000 строк и новые отказы `503 RECENT_WINDOW_UNAVAILABLE`. Обычные ключи также сохраняют исходные query-параметры legacy-чтения сообщений; фильтр защищённых селекторов READONLY сохранён.

### NEW-0929-19: запись значений списочных свойств каталога через V1

Через API Вайбкод доступны создание, частичное изменение и удаление вариантов списочного свойства: `POST /v1/catalog-product-property-enums`, `PATCH /v1/catalog-product-property-enums/:id` и `DELETE /v1/catalog-product-property-enums/:id`. При частичном изменении отсутствующие обязательные поля Битрикс24 подставляются из текущей записи.

### NEW-0929-20: причина и готовый перенос в отказе BOT_ACCESS_DENIED

Ответ `403 BOT_ACCESS_DENIED` (бот привязан к другому ключу API) несёт новые необязательные поля: `error.cause` со значением `bot_other_key`, `error.fix` и `error.hint`. Если вызывающий ключ может сам перенести бота на себя, `error.fix` — `{ "action": "transfer_bot", "via": "same_key", "path", "body" }`. В `path` — готовый маршрут `POST /v1/bots/{botId}/transfer` с идентификатором бота из запроса, в `body` — тело с идентификатором самого вызывающего ключа. Ключ, к которому привязан бот, в ответе не называется. Иначе `error.fix.action` — `none`, а `error.hint` называет причину. Код, статус и `error.message` не изменились. Разбор — [Авторизация, ключи и права](/docs/errors/auth#bot_access_denied-403).
